3 分钟快速生成代码
输入想法,AI 即刻生成可运行代码
在聚宽(JoinQuant)平台中,利用投资组合优化器(portfolio_optimizer)可以帮助策略在既定约束下实现资产的最优配置。本文将介绍如何使用 MaxSharpeRatio 目标函数构建夏普比率最大化的量化投资策略。
MaxSharpeRatio(rf=0.0, weight_sum_equal=1.0, count=250)
rf: 年化无风险利率,默认为 0.0。weight_sum_equal: 组合总权重的约束值,默认为 1.0。count: 计算收益率和协方差矩阵的历史交易日窗口,默认为 250 天。portfolio_optimizer(date, securities, target, constraints, bounds, ...)
date: 优化计算发生的日期(通常传入 context.previous_date 避免未来函数)。securities: 备选股票/基金池列表。target: 优化目标,此处设为 MaxSharpeRatio 实例。constraints: 约束条件列表(如行业约束、换手率约束等)。bounds: 单标的权重上下限约束,例如 [Bound(0, 0.1)] 表示单只标的持仓不超过 10%。以下策略演示了每月初通过组合优化器对股票池进行重新打分与权重优化,构建夏普比率最大化投资组合的完整流程:
import pandas as pd
from jqdata import *
from jqlib.optimizer import *
def initialize(context):
# 设定沪深 300 作为基准
set_benchmark('000300.XSHG')
# 开启真实价格动态复权模式
set_option('use_real_price', True)
# 设置股票交易手续费
set_order_cost(OrderCost(close_tax=0.001, open_commission=0.0003, close_commission=0.0003, min_commission=5), type='stock')
# 定时按月调仓
run_monthly(rebalance, monthday=1, time='09:30', reference_security='000300.XSHG')
def rebalance(context):
# 1. 确定股票池(例如沪深300前20只股票)
stocks = get_index_stocks('000300.XSHG')[:20]
# 2. 设置优化目标:夏普比率最大化
target = MaxSharpeRatio(rf=0.0, weight_sum_equal=1.0, count=250)
# 3. 设置边界条件:每只股票权重范围在 0% 到 15% 之间
bounds = [Bound(low=0.0, high=0.15)]
# 4. 运行投资组合优化器
optimized_weight = portfolio_optimizer(
date=context.previous_date,
securities=stocks,
target=target,
constraints=[],
bounds=bounds,
default_port_weight_range=[0.0, 1.0],
ftol=1e-09,
return_none_if_fail=True
)
# 5. 执行调仓
if optimized_weight is not None:
# 卖出不在优化结果或权重归零的持仓
for stock in list(context.portfolio.positions.keys()):
if stock not in optimized_weight or optimized_weight[stock] == 0:
order_target_value(stock, 0)
# 按优化分配的权重下买单
total_value = context.portfolio.total_value
for stock, weight in optimized_weight.items():
target_value = total_value * weight
order_target_value(stock, target_value)
log.info("优化调仓成功,目标权重为:", optimized_weight)
else:
log.warn("投资组合优化失败,保持现有持仓!")
portfolio_optimizer 时,date 参数应传入 context.previous_date,切勿使用当天或未来的日期。None,代码中需做好异常兼容。initialize 中使用 set_option('use_real_price', True) 开启真实价格模式,以保障回测和撮合逻辑贴近实际交易环境。