首页 > 其他分享 >手把手教你,利用机器学习模型,构建量化择时策略(附全流程代码)

手把手教你,利用机器学习模型,构建量化择时策略(附全流程代码)

时间:2024-07-04 23:02:33浏览次数:3  
标签:SVM 附全 手把手 模型 择时 print train test data

歌神演唱会人脸识别抓逃犯,阿尔法狗战胜人类围棋手,AI绘图《太空歌剧院》惊艳艺术博览会,ChatGPT一问解千愁~~~这些震撼成果的背后,都是人工智能在蓬勃发力。

图片

既然人工智能/机器学习这么厉害,在其他领域都取得了丰硕的成果和巨大的成功,那么是不是可以让计算机帮咱预测市场大盘、选择和买卖股票/期货/外汇/大饼,解放双手,丰衣足食,岂不美哉?

已经有非常多的机构开展这方面的研究和实践了,今儿个咱也来探索一下,机器学习在量化投资当中的应用,从零开始走通基于机器学习的量化指数择时模型的开发全流程。

目录

零. 机器学习,浅尝一下

一. 收集数据

二. 数据准备

三. 选择/建立模型

四. 训练模型

五. 测试模型

六. 调节参数


零. 机器学习,浅尝一下

人类发现规律一般采用的是归纳演绎法,对观察到的大量现象进行归纳,在心中形成规律,然后再遇到类似的情况,就可以迅速做出预测和判断,比如说“朝霞不出门,晚霞行千里”、“瑞雪兆丰年”、“狗打喷嚏天要晴”,这都是老祖先归纳演绎法的结晶,可能不是每回都灵验。

图片

机器学习和人类的思考过程非常相似,把历史数据输入到模型当中,训练出一个能完成特定任务的数学模型,等到有新的数据出现时,就把新数据输入到训练好的模型当中,这就会输出一个预测的结果,特别地,机器学习在识别非线性规律方面,相较于人脑更有优势。

具体结合咱这次的目标进行说明,咱这次的任务就是利用机器学习模型,预测沪深300指数第二天的涨跌情况,输入的数据就是沪深300指数的开高低收行情数据,将这些数据输入到支持向量机(Support Vector Machine,SVM)当中进行模型训练,待SVM训练好之后,输入今天的行情数据,就能输出对第二天行情的预判。

为什么选择SVM呢?因为咱这次使用的数据集是沪深300指数的日线行情数据,它自2005年上市以来,拢共才四千多个交易日,换句话说,也才四千多个样本点,相对于几百万上千万的“大数据”来说,这充其量才算一个“小样本”,这无疑是一个非常适合SVM的应用场景。

因为在深度学习(一般需要大数据“投喂”)尚未全面兴起时,SVM由于其较高的小样本预测准确率,并且能够解决非线性分类问题,属于当时机器学习方法潮流圈中的扛把子。

SVM很能打,但本身并不是非常复杂,今儿个不抠数学细节,大白话讲讲SVM是什么有什么用,以免没开始就把大伙儿劝退了。

图片

SVM最初的设计是用来解决二分类问题,后来扩展到多分类问题,“预测沪深300指数涨跌”就属于典型的二分类问题,“涨”是一个类别,“跌”就是另一个类别。

它通过寻找一个最大间隔超平面(上图黑斜线)将两类样本线性区分开来,并且保证两侧样本的最近边缘点到这个平面的距离是最大的,由于最大间隔超平面仅取决于两个类别的边缘点,例如上图中被红线和蓝线穿过的红点和蓝点,这些点就被称为支持向量,这就是“支持向量机”名称的由来。

但现实世界很奇妙,有线性可分的数据集,就有非线性可分的数据集,那遇到非线性可分的情况怎么办?

图片

那也有办法,SVM引入了核函数,可以将低维不可分的数据映射到高维线性可分,如上图,二维不可分就映射到三维,常用的核函数有线性核、多项式核、高斯核(RBF核)和Sigmoid核。

图片

但在现实当中,由于噪声和极端样本点的存在,数据集无论在低纬和高维都可能出现线性不可分的情况,于是乎,SVM当中引入了松弛变量的概念,允许了最大间隔超平面不用完美区分两个类别,允许错误分类的存在,SVM通过惩罚系数C控制这些错误分类的容忍程度,C值越高分类准确率越高,但数值过高容易导致过拟合,C值过低则会导致准确率受损。

SVM唠完了,咱来说说一般机器学习建模的流程,一般分为6步走,按照先后顺序分别是收集数据、准备数据、选择/建立模型、训练模型、测试模型和调节参数。量化,没有白走的路,每一步都算数,下文咱一步一步地走一遍~

图片

一. 收集数据

巧妇难为无米之炊,第一步咱要获取到最原始的建模数据,对于指数的日线数据而言,有非常多的免费获取渠道,只要能获取到指数的日期(date)、开盘价(open)、最高价(high)、最低价(low)和收盘价(close)就可以了。

在此处以tushare为例,获取沪深300指数自2005年4月8日上市以来的全部行情数据,它是一个免费、开源的python财经数据接口包,网址是:http://tushare.org/。

导入tushare包之后,使用它的get_k_data函数,就可以获得沪深300指数的历史K线数据,返回的数据格式是dataframe,咱只选取开高低收数据,并将日期(字符串格式)设置为索引。

import numpy as np
import pandas as pd
import talib
import warnings
warnings.filterwarnings('ignore')
import tushare as ts

data = ts.get_k_data(code='hs300', start='2005-04-08', end='2022-11-08', ktype='D')
data = data.set_index('date')
data = data[['open', 'high', 'low', 'close']]
print('样本数目:%d' %data.shape[0])
print(data.head(10))
print(45*'-')
print(data.tail(10))

图片

二. 数据准备

有了原始数据之后,咱还要进一步进行加工和处理,主要工作是变量选择、确认标签和数据清洗。

变量选择在量化投资当中叫“因子选择”,就是用哪些因子(factor)进行选股择时那些,在机器学习领域一般叫“特征选择”,指定用哪些特征(feature)来作为算法模型的输入。

在这里咱用到因子分别是EMA值(ema)、价格波动率(stddev)、价格斜率(slope)、RSI值(rsi)和威廉指标值(wr),此处咱利用talib包丝滑地完成计算,它是一款量化圈驰名、彪悍强大的第三方技术分析指标计算包。

data['ema'] = talib.EMA(data['close'].values, timeperiod=20)
data['stddev']= talib.STDDEV(data['close'].values, timeperiod=20, nbdev=1)
data['slope'] = talib.LINEARREG_SLOPE(data['close'].values, timeperiod=5)
data['rsi'] = talib.RSI(data['close'].values, timeperiod = 14)
data['wr'] = talib.WILLR(data['high'].values, data['low'].values, data['close'].values, timeperiod=7)
data.tail(10)

图片

确认标签呢,就是给这个样本点打上类别标签,由于咱是预测指数第二天的涨跌情况,于是,咱先计算出每个样本第二天的涨幅(pct),如果第二天上涨,则设置标签(rise)为1,反之为0。

由于指数数据一般异常情况不是很多,如果有空值,咱把空值删除就好了。

data['pct'] = data['close'].shift(-1) / data['close'] - 1.0
data['rise'] = data['pct'].apply(lambda x: 1 if x>0 else 0)
#删除缺失值
data = data.dropna()
data.tail(10)

图片

三. 选择/建立模型

选择/建立模型就是需要确定自己这次使用哪种机器学习模型,是支持向量机SVM呢,还是神经网络NN呢,亦或是随机森林RF呢,或者其他的模型。

在之前已经说过了,咱是用SVM模型,原因和原理不再赘述,为了方(tou)便(lan)实现和建立模型,咱可以直接从Scikit-learn(简称sklearn)中导入,它是非常流行的Python免费机器学习库 ,具有各种分类、回归和聚类算法,一般配合numpy数据格式使用。

四. 训练模型

在这里,咱需要把整个数据集分拆为训练集和测试集,因为除了训练模型之外,咱还要留出一部分数据来验证训练出来模型的优劣。

一般来说,将完整数据集80%的样本作为训练集,剩余20%的样本作为测试集,要注意的是,这里要将dataframe中的因子数据转换成numpy的ndarray数组格式,因为这种数据类型更适配sklearn。

# 划分训练集和测试集
num_train = round(len(data)*0.8)
data_train = data.iloc[:num_train, :]
data_test = data.iloc[num_train:, :]
# 训练集数据和标签
X_train = data_train[['ema', 'stddev', 'slope', 'rsi', 'wr']].values
y_train = data_train['rise']
# 测试集数据和标签
X_test = data_test[['ema', 'stddev', 'slope', 'rsi', 'wr']].values
y_test = data_test['rise']
print(X_train[:10])
print(45*'-')
print(X_test[:10])

在划分数据集之后,还有非常重要的一步,那就是对数据进行标准化处理,这是因为每个因子的数值量纲差别太大,例如指数EMA的均值是2919.6,而RSI的均值是52.7,这样会造成SVM对某些因子的“偏心”。

在此处,采用“(原始值 - 均值) / 标准差”的方法对数据进行标准化处理,处理过后,每个因子的均值都会变为0,标准差变为1.0。

from sklearn.preprocessing import StandardScaler

print('---标准化之前---')
print('训练集的均值:')
print(X_train.mean(axis=0))
print('训练集的标准差:')
print(X_train.std(axis=0))

# 对数据进行标准化
scaler = StandardScaler()
X_train = scaler.fit_transform(X_train)
X_test = scaler.transform(X_test)

print('---标准化之后---')
print('训练集的均值:')
print(X_train.mean(axis=0))
print('训练集的标准差:')
print(X_train.std(axis=0))

图片

数据标准化处理之后,就可以将训练集数据输入SVM当中,代码实现很简单,从sklearn的svm模块当中导入SVM分类器SVC,创建实例对象后,将训练集因子数据和对应标签塞进fit函数就行了,SVM模型的惩罚系数使用默认值1.0,核函数也用默认的RBF核函数,训练过程非常快,不用一个东的时间,就把SVM分类器训练好了。

from sklearn.svm import SVC

classifier = SVC(C=1.0, kernel='rbf')
classifier.fit(X_train, y_train)
print(classifier)

图片

五. 测试模型

至此,SVM分类器已经训练好了,把因子数据塞进predict函数,就能输出每个样本的预测值,咱分别把训练集和测试集的预测标签插回到原来的数据集当中,用来计算预测的准确率。

y_train_pred = classifier.predict(X_train)
y_test_pred = classifier.predict(X_test)
data_train['pred'] = y_train_pred
data_test['pred'] = y_test_pred
accuracy_train = 100 * data_train[data_train.rise==data_train.pred].shape[0] / data_train.shape[0]
accuracy_test = 100 * data_test[data_test.rise==data_test.pred].shape[0] / data_test.shape[0]
print('训练集预测准确率:%.2f%%' %accuracy_train)
print('测试集预测准确率:%.2f%%' %accuracy_test)

输出结果:

训练集预测准确率:57.52%测试集预测准确率:52.35%

从结果当中看出,训练集的预测准确率明显比测试集的高,这是因为整个模型都是在训练集数据上训练出来的,对测试集数据则还很“陌生”,这就相当于高考数学考卷都是你们学校的数学老师出的,整体来看,你们的平均分就非常可能比其他同级别的学校高。

光看准确率还不够直观,咱还要看一下如果纯粹按照这个择时模型的预测结果进行投资,能获得多少收益,此处只使用测试集进行模拟。

假设指数可以多空交易,如果模型预测为1(上涨),第二天策略的收益率就是指数的涨幅,如果模型预测为0(下跌),第二天策略的收益率就是指数的涨幅的相反数,有了每天的日收益率之后,通过dataframe自带的累乘函数cumprod,就可以得到择时策略和沪深300指数的净值曲线,为了方(tou)便(lan)起见,不考虑交易费率,以及按照收盘价成交。

import matplotlib.pyplot as plt

#策略日收益率
data_test['strategy_pct'] = data_test.apply(lambda x: x.pct if x.pred>0 else -x.pct, axis=1)
#策略和沪深300的净值
data_test['strategy'] = (1.0 + data_test['strategy_pct']).cumprod()
data_test['hs300'] = (1.0 + data_test['pct']).cumprod()
# 粗略计算年化收益率
annual_return = 100 * (pow(data_test['strategy'].iloc[-1], 250/data_test.shape[0]) - 1.0)
print('SVM 沪深300指数择时策略的年化收益率:%.2f%%' %annual_return)

#将索引从字符串转换为日期格式,方便展示
data_test.index = pd.to_datetime(data_test.index)
ax = data_test[['strategy','hs300']].plot(figsize=(16,9), color=['SteelBlue','Red'],
                                          title='SVM 沪深300指数择时策略净值  by 量化君')
plt.show()

图片

六. 调节参数

从上一步的测试当中看出,训练集和测试集的预测准确率只有57%和52%,不算理想,说明还有很大的提升空间,还可以对模型进行优化改进。

比如说,现在使用的5个因子,还没有反应到价格波动的本质,还可以增改更多的因子。

还比如说,SVM模型当中的惩罚系数C过小,对错误样本的容忍度过高,RBF核函数不适合作为这个数据集的映射转换函数。

再比如说,甚至连SVM模型本身也是一个参数,也可以更改,比如说可以换成其他的机器学习分类模型。

也就是说到这调节参数这一步,如果训练好的模型结果不能让自己满意,就可以重新将前5步走一遍。

咱终于吭哧吭哧走完了,利用机器学习构建量化择时策略的全流程,相信大伙儿对机器学习相关概念和建模流程也有了初步的了解,基于这个建模框架流程,将来的你可以玩得更花,可以采用更高频的数据、更鲁棒的模型、更多的交易标的、更有效的因子、更有趣的预测任务,以及~~~遇见更好的自己。

参考资料

周志华,2016年1月,书籍《机器学习》

华泰金工,2017年8月,研报《人工智能选股之支持向量机模型》

阿泽,2020年6月,知乎《【机器学习】支持向量机 SVM(非常详细)》

标签:SVM,附全,手把手,模型,择时,print,train,test,data
From: https://blog.csdn.net/iamquantman/article/details/140163582

相关文章

  • 复现网红阻力支撑指标RSRS,手把手教你构建大盘择时策略
    之前写过一篇利用RSRS指标做ETF轮动的文章,可能是因为回测绩效看起来还不错,其后就有不少小伙伴陆陆续续来询问,想不到还有那么多人关注,于是本期文章就想掰开了揉碎了唠唠RSRS,从数据获取、计算细节一直聊到策略构建,不藏着掖着,每一步都有对应代码。我当初关注到RSRS,是因为当时无......
  • (必看图文)Hadoop集群安装及MapReduce应用(手把手详解版)
    前言    随着大数据时代的到来,处理和分析海量数据已成为企业和科研机构不可或缺的能力。Hadoop,作为开源的分布式计算平台,因其强大的数据处理能力和良好的可扩展性,成为大数据处理领域的佼佼者。本图文教程旨在帮助读者理解Hadoop集群的安装过程,并通过MapReduce应用实例,......
  • 手把手教你如何用python写一个经典小游戏(仅需100行以内的代码)
    创作灵感小时候也就是大概十几年前的时候,智能触屏手机还未大量普及,移动网络还是2G,大部分人用的都是小灵通,里面只有几款经典的游戏,比如俄罗斯方块,贪吃蛇等。还记得以前自己玩的不亦乐乎。如今网络发展迅速,通讯设备越来越智能化,集成化,这些上世纪的经典游戏似乎早已淡忘人们的视......
  • 基于python语言的网页设计(手把手教你设计一个个人博客网站)
     总体的设计思路设计网页的思路涉及多个方面,从前端的页面结构和样式,到后端的数据处理和逻辑实现。1.确定网站的需求和功能首先要明确网站的功能需求,比如用户注册登录、博客文章发布和展示、评论系统等。2.选择技术栈选择适合的框架和工具。对于Python,常用的Web框架包括Fl......
  • Hyper-V虚拟机固定IP地址(手把手教设置)
    链接虚拟机修改网络配置文件输入指令sudovi/etc/sysconfig/network-scripts/ifcfg-eth0然后输入 按 i 键再按回车(enter)进入编辑模式修改配置(这几项)其中 IPADDR就是你想给虚拟机固定的IP地址多台的话只需要修改这个IP就行其他不变BOOTPROTO=staticI......
  • 手把手教你:如何在51建模网免费下载3D模型?
    作为国内领先的3D互动展示平台,51建模网不仅汇聚了庞大的3D模型资源库,供用户免费下载,更集成了在线编辑、格式转换、内嵌展示及互动体验等一站式功能,为3D创作者及爱好者搭建起梦想与现实的桥梁。如何在51建模网免费下载3D模型?按照下面几个步骤即可轻松下载:01、筛选可下载模型......
  • AI唱古诗大片,粉丝10W+, 手把手免费教你
    看到别人用AI做唱古诗的视频动画,小红薯10W+粉丝,后期接广变现。从YOUTUBE上学来的方法,自己实操起来感觉还是很简单的。打开思路,AI时代任何有亮点的创作都会有受众。百度网盘请输入提取码百度网盘为您提供文件的网络备份、同步和分享服务。空间大、速度快、安全稳固,支......
  • AI唱古诗大片,粉丝10W+, 手把手免费教你
     看到别人用AI做唱古诗的视频动画,小红薯10W+粉丝,后期接广变现。从YOUTUBE上学来的方法,自己实操起来感觉还是很简单的。打开思路,AI时代任何有亮点的创作都会有受众。百度网盘请输入提取码百度网盘为您提供文件的网络备份、同步和分享服务。空间大、速度快、安全稳固,支......
  • 手把手带你使用JWT实现单点登录
    JWT(英文全名:JSONWebToken)是目前最流行的跨域身份验证解决方案之一,今天我们一起来揭开它神秘的面纱!一、故事起源说起JWT,我们先来谈一谈基于传统session认证的方案以及瓶颈。传统session交互流程,如下图:当浏览器向服务器发送登录请求时,验证通过之后,会将用户信息存入seesion中......
  • 手把手搞定报名亚马逊科技认证
    亚马逊云科技认证考试为我们这些技术从业者提供了提升专业技能的机会。无论选择线上还是线下考试,每种方式都有其独特的优势和挑战。选择合适的考试方式将帮助我们更好地展示自己的技术水平。以下是我对不同考试方式的优缺点介绍,以及各科目的考试代码。希望这些信息能帮助大......