# 研究环境或策略中使用的选股函数
# 规则:
# 1. 销售净利率为负(最近财报)
# 2. 经营活动现金流净额为负(最近财报)
# 3. 资产负债率 > 65%(最近财报)
# 4. 仅考察中信一级行业为"电力设备及新能源"的股票(可根据需要修改)
from jqdata import *
import pandas as pd
def filter_stocks(context, stock_list):
"""
从stock_list中剔除财务风险较高的股票
返回剔除后剩余的股票列表
"""
# 获取当前日期
current_date = context.current_dt.date()
# 准备财务数据查询日期(取最新财报,一般用上一个季度末)
# 聚宽中取最近一个财报期的数据可以使用如下方式
# 这里简化为查询最新可得的季度数据
q = query(
valuation.code,
indicator.net_profit_margin, # 销售净利率(%)
cash_flow.operating_net_cash_flow, # 经营活动现金流净额(元)
balance.total_liabilities / balance.total_assets * 100 # 资产负债率(%)
).filter(
valuation.code.in_(stock_list)
)
# 执行查询,获取最新季度数据
df = get_fundamentals(q, date=current_date)
if df.empty:
return stock_list # 无数据则返回原列表
# 设置索引便于操作
df.set_index('code', inplace=True)
# 风险标记列,初始为False(无风险)
df['risk'] = False
# 规则1:销售净利率为负(注意:net_profit_margin是百分比值,比如-5表示-5%)
df.loc[df['net_profit_margin'] < 0, 'risk'] = True
# 规则2:经营活动现金流净额为负
df.loc[df['operating_net_cash_flow'] < 0, 'risk'] = True
# 规则3:资产负债率 > 65%
df.loc[df['expr1'] > 65, 'risk'] = True
# 获取有风险的股票代码列表
risk_codes = df[df['risk']].index.tolist()
# 从原始列表中剔除有风险的股票
filtered_list = [code for code in stock_list if code not in risk_codes]
# 可选的日志输出,便于观察
log.info('原始股票数:{},剔除风险股票数:{},剩余:{}'.format(
len(stock_list), len(risk_codes), len(filtered_list)))
return filtered_list
def initialize(context):
# 初始化函数,设定基准等
run_daily(prepare_stock_pool, time='before_open')
def prepare_stock_pool(context):
"""
每日开盘前准备股票池
"""
# 1. 获取原始股票池,例如全部A股,但为了效率可限定为某些指数
# 这里以沪深300为例,可替换为其他列表
# original_stocks = get_index_stocks('000300.XSHG') # 沪深300
# 或者获取中信一级行业“电力设备及新能源”的全部股票
industry_code = '电力设备及新能源' # 聚宽中信一级行业名称
stock_list_in_industry = get_industry_stocks(industry_code, date=context.current_dt.date())
if not stock_list_in_industry:
log.warn('未找到行业股票,请检查行业名称')
return
# 2. 应用过滤函数
context.filtered_stocks = filter_stocks(context, stock_list_in_industry)
# 3. 可将过滤后的股票赋值给g.secure_stock用于策略交易
g.secure_stock = context.filtered_stocks
log.info('今日安全股票池:{}'.format(g.secure_stock))
# 注意:以上代码需要在聚宽平台上运行,并确保行业名称准确。
# 如果行业名称不匹配,可以先用如下代码查看聚宽支持的行业分类:
# from jqdata import get_industries
# print(get_industries(name='sw_l1')) # 申万一级行业
# print(get_industries(name='zjw')) # 中证行业
# 本示例使用的是中信一级行业,需要确认聚宽源数据中是否有此分类,如无请改用申万行业。
2026-02-26