因子构建与标注——自定义标注
由iquant创建,最终由iquant 被浏览 58 用户
导语
本文标题为自定义标注,其实就是想告诉大家如何灵活地对数据进行标注,从而得到预测能力更强的机器学习算法。
认识分类和回归
谈标注一词之前,我们先简单了解机器学习算法中的分类和回归。
分类问题是监督学习的一个核心问题。在监督学习中,当输出变量Y取有限个离散值时,预测问题便成为分类问题。监督学习从数据中学习一个分类模型,称为分类器(classifier)。分类器对新的输入进行输出的预测,这个过程称为分类。
当输出变量Y为有限个离散值时,成为分类问题,那如果输出变量Y是连续值时,又该怎样处理呢?可能大家马上想到这其实就是回归问题,用回归算法就可以解决。的确如此,但很多时候,回归算法预测效果不好。此时,我们可以对连续性数值进行标注,将Y标注为多个类别,这时又可以通过分类算法来解决。对数据进行标注在图像识别、文本分析、语音分析中经常遇到,标注的思想也广泛存在于机器学习领域。将数据标注为多个离散值成为分类标注,将数据标注为连续性数据称为回归标注。
对股票进行标注然后结合股票的特征是否能训练出一个有预测能力的模型呢?这正是许多机器学习算法在在量化选股领域的尝试。股票标注可以直接影响到AI策略的效果,可见其重要性,接下来我们详细介绍如何对股票进行标注。
数据标注应该注意
数据标注应注意的几点:
- 数据标注既包括分类标注也包括回归标注。分类标注为将数据分为具有区分性的多个类别,回归标注后数据为连续性数据。分类标注比较常用。
- 数据标注时,应尽可能结合机器学习的算法预测目的。如果目标是想预测收益率较高的股票,在标注时应结合股票收益率;如果目标是想预测波动率较低的股票,在标注时应结合股票波动率。
- 数据标注时,应尽可能将数据区别开来,但又不可分得太细。比如,通过股票收益率将股票分为五类,分别为高收益、较高收益、一般、较低收益、低收益,因此此时就可以采取分类算法。如果分得太细,可能算法在训练集上会学到不少数据噪音,泛化能力不强。
- 分类标注中标注后的数据不一定是具体的类别,而是具体的数值。比如,'数值>=20'为高收益股票,"15<数值<20"为较高收益股票,"10<数值<15"为一般股票,“5<数值<10”为较低收益股票,“数值<5”为低收益股票。
开发AI策略
数据标注和特征工程一样重要,共同决定了机器学习算法的预测能力。数据标注确定的标注结果和特征工程确定的因子数据合并起来就形成了训练集数据,已经可以训练出一个学习算法。当我们得到学习算法后,传入测试集的因子数据就可以得到预测结果,通过回测就可以开发AI策略。
在BigQuant上,数据标注有专门的模块接口,方便大家高效灵活地进行标注。本文简单枚举了一些标注数据的应用例子,希望大家理解以便开发出更好的AI策略。
首先我们在可视化策略中建立如下流程
如图所示,在m1输入特征模块中我们构建表达式特征,接下来在m2中我们继续拖入输入特征模块,通过表达式引擎自定义标注。我们可以通过改变m2模块中的标注代码实现不同的自定义标注方式,最后再通过m3数据抽取模块来抽取数据。下面列举几种方式的实现:
根据收益率进行分类标注
模块代码示例
## 将m1中除去date和instrument以外的全部特征导入进来
input_1.* EXCLUDE(date, instrument)
## 计算收益:5日收盘价(作为卖出价格)除以明日开盘价(作为买入价格)
m_lead(close, 5) / m_lead(open, 1) AS _future_return
## 极值处理:用1%和99%分位的值
c_quantile_cont(_future_return, 0.01) AS _future_return_1pct
c_quantile_cont(_future_return, 0.99) AS _future_return_99pct
clip(_future_return, _future_return_1pct, _future_return_99pct) AS _clipped_return
## 将分数映射到分类,这里使用20个分类
c_cbins(_clipped_return, 20) AS label
在表达式过滤条件中,过滤掉一字涨停:
通过matplotlib可以查看输出结果
画图代码示例
import matplotlib.pyplot as plt
# 统计每个label的计数,并排序
label_counts = df['label'].value_counts().sort_index()
# 设置画布大小
plt.figure(figsize=(10, 6))
# 绘制柱状图,并设置柱子之间的间隙
bars = plt.bar(label_counts.index, label_counts.values, color='skyblue', width=0.6)
# 添加标题和标签
plt.title('Label Distribution', fontsize=16)
plt.xlabel('Label', fontsize=14)
plt.ylabel('Count', fontsize=14)
# 添加网格线
plt.grid(axis='y', linestyle='--', alpha=0.7)
# 显示图表
plt.show()
这幅柱状图描述了整个训练集中各个label的分布情况,本例中将收益率分为0到19个档级,柱状图高度表示各个档级的样本数量。
代码解读
-
根据未来几天的收益率进行标注可以直接修改
m_lead(close, 5)
中的5。 -
c_quantile_cont(_future_return, 0.01) AS _future_return_1pct
c_quantile_cont(_future_return, 0.99) AS _future_return_99pct
clip(_future_return, _future_return_1pct, _future_return_99pct) AS _clipped_return
利用分位数对极值进行处理。 -
c_cbins(_clipped_return, 20)
是按照收益率等间隔分为20类,每个标注类别的之间的收益率间隔大小相等。
根据收益率大小标注
m3模块代码示例
## 将m1中除去date和instrument以外的全部特征导入进来
input_1.* EXCLUDE(date, instrument)
## 计算收益:5日收盘价(作为卖出价格)除以明日开盘价(作为买入价格)
m_lead(close, 5) / m_lead(open, 1) AS _future_return
## 极值处理:用1%和99%分位的值
c_quantile_cont(_future_return, 0.01) AS _future_return_1pct
c_quantile_cont(_future_return, 0.99) AS _future_return_99pct
clip(_future_return, _future_return_1pct, _future_return_99pct) AS _clipped_return
## 将分数映射到分类,这里使用20个分类
c_cbins(_clipped_return, 20) AS label
据经波动率调整后的收益率标注
标注数据为:经过波动率调整后的收益率(类似于夏普比率) m2模块代码示例
## 将m1中除去date和instrument以外的全部特征导入进来
input_1.* EXCLUDE(date, instrument)
## 计算经波动率调整后的收益
m_lead(close, 5) / m_lead(open, 1) / m_stddev(m_lead(close, 2) / m_lead(open, 1), 5) AS _future_return
## 极值处理:用1%和99%分位的值
c_quantile_cont(_future_return, 0.01) AS _future_return_1pct
c_quantile_cont(_future_return, 0.99) AS _future_return_99pct
clip(_future_return, _future_return_1pct, _future_return_99pct) AS _clipped_return
## 将分数映射到分类, 这里使用20个分类
c_cbins(_clipped_return, 20) AS label
绘制标注分布图如下:
根据收益率排序计算标注
m3模块代码示例
## 将m1中除去date和instrument以外的全部特征导入进来
input_1.* EXCLUDE(date, instrument)
## 计算经波动率调整后的收益
rank(m_lead(close, 5) / m_lead(open, 1)) AS _future_return
## 极值处理:用1%和99%分位的值
c_quantile_cont(_future_return, 0.01) AS _future_return_1pct
c_quantile_cont(_future_return, 0.99) AS _future_return_99pct
clip(_future_return, _future_return_1pct, _future_return_99pct) AS _clipped_return
## 将分数映射到分类, 这里使用20个分类
c_cbins(_clipped_return, 20) AS label
\
自定义计算标注
可以通过自定义模块编写代码自定义计算标注值,平台默认识别label列为标注列。
代码示例
https://bigquant.com/codesharev2/64ec2b90-87b3-4960-a56b-844ee332f3d0