股票市场预测模型(股票预测模型的搭建)_炒股学院_景合财经知识网_景合财经景合财经

景合财经
景合财经知识网站

股票市场预测模型(股票预测模型的搭建)

数据描述

通过上一篇文章的介绍,我们学习到,可以从Tushare提供的API数据接口,获得基本的股票数据,包括开盘价、收盘价、最高价、最低价成交量等一系列数据。我们可以将所有股票的历史数据收集保存起来,构造数据集。

股票市场预测模型

下面是我们获取的数据记录。

股票市场预测模型

根据已有的数据构建股票预测思路

预测的思路有很多种,一方面看自己的想法,一方面可以借鉴前人的经验。当然预测思路不是最最重要的,重要的是,能够高胜率的挑选出股票。

本文的思路是,使用前n天以发生的股票行情数据,作为预测输入,第n+2天的第n+1天差价(涨跌幅)作为预测目标进行训练。我们认为具体的涨幅值得预测有难度,并且没必要那么精细,目标是只要能跳出涨得就好了。

我们将涨幅划分为0-5%,大于5%两类,分别给标签类别1,类别2.

跌幅同样划分为0-5%,大于5%两类,分别给标签类别3,类别4.

这样股票预测的问题就变成了一个4分类问题。

我们将n取为60天。时间周期的选取没有确切的依据,本文中的60是适当的选取,时间周期选取是好是坏需要实验对比得出。

使用前60天数据,预测第61天买进,第62卖出会是出现第几类的情况。

数据预处理

原有数据是一天一条记录,且数据记录中所有的股票数据都在一块。根据需求我们要将前60天的一只股票的数据作为输入特征,所以需要进行根据股票名称进行分组、根据时间进行排序,然后按60天做时间序列处理。为了消除变量之间的量纲差异,又进行了特征归一化处理。

# 读取原始数据,只保留需要使用的列total_data = pd.read_csv(orgin_data, usecols=["open_hfq", "high_hfq", "low_hfq", "close_hfq", "amount", "volume" , "stock_date", "stock_num"])# 根据股票代码排序,相同的股票代码按照交易日期排序。# inplace参数表示不需要返回排序后的结果,直接覆盖原变量即可total_data.sort_values(by=['stock_num', 'stock_date'], inplace=True)# 根据股票代码分组g_stock_num = total_data.groupby(by=["stock_num"])# 针对每一组股票,分别计算收益gate,其定义为:(下下一个交易日的开盘价 / 下一个交易日的开盘价) - 1# 对gate乘以100,使之变成百分比形式(0.09 -> 9,表示9%)# 使用np.round函数保存两位小数,之后的数字丢弃(9.8346474 - > 9.83)total_data["gate"] = np.round( (100 * (g_stock_num.shift(-2)["open_hfq"] / g_stock_num.shift(-1)["open_hfq"] - 1)), 2)# 重新调整列的顺序,为接下来处理成输入、输出形式做准备total_data = total_data[["open_hfq", "high_hfq", "low_hfq", "close_hfq", "amount", "volume", "gate", "stock_date", "stock_num"]]# 将调整列顺序后的代码,重新按照股票代码分组g_stock_num = total_data.groupby(by=["stock_num"])print()# 拿time_step个交易日的数据(默认为60个交易日),进行标准化def func_stand(data_one_stock_num, time_step): # 通过apply进入函数内的数据,其股票名为data_one_stock_num.name,类型为pd.dataFrame # 即,进入此函数的数据为所有名为data_one_stock_num.name的集合 # dataFrame.shape:(num , 11), num是这个股票出现的次数 # 剔除这3个输出特征跳出循环,输入特征进行标准化 for colu_name in data_one_stock_num.columns: if colu_name in ["gate", "stock_date", "stock_num"]: continue # 只针对输入数据进行标准化,标准化算法为: (原始数据 - 平均值) / 标准差 # 这里每一次for循环,都拿出了1列数据,针对这一列进行标准化并覆盖原数据 data_one_stock_num[colu_name] = ( (data_one_stock_num[colu_name] - data_one_stock_num[colu_name].rolling(time_step).mean()) / data_one_stock_num[colu_name].rolling(time_step).std()) return data_one_stock_num# 将经过标准化的数据处理成训练集和测试集可接受的形式def func_train_test_data(data_one_stock_num, time_step): print("正在处理的股票代码:%06s" % data_one_stock_num.name) # 提取输入列(对应train_x) data_temp_x = data_one_stock_num[["open_hfq", "high_hfq", "low_hfq", "close_hfq", "amount", "volume" ]] # 提取输出列(对应train_y) data_temp_y = data_one_stock_num[["gate", "stock_date", "stock_num"]] data_res = [] # for循环从time_step - 1开始,因为前time_step - 1个数据不满足time_step条件 # 例如:time_step为60,即需要60个交易日的数据制成训练集的一个输入,但某只股票因为停牌等原因,只有50个交易日的数据。那么它就可以跳过了,不满足最低数目的要求 ''' 在这里转置矩阵时,需要根据现在的输入特征数量调整''' for i in range(time_step - 1, len(data_temp_x.index)): a = data_temp_x.iloc[i - time_step + 1: i + 1].values.reshape(1, time_step * 6) b = data_temp_y.iloc[i][["gate", "stock_date", "stock_num"]].values.reshape(1, 3) single_data = np.hstack((a, b)) data_res.append(single_data.flatten()) data_res = np.asarray(data_res) print("shape: ", data_res.shape) if len(data_res) != 0: # 使用末尾添加的形式,将各个股票的数据依次添加进设定的路径中。 # index参数表示是否需添加一列序号,header表示是否需要添加列头,mode表示选择哪一种模型进行csv操作(类似于open函数的模型) pd.DataFrame(data_res).to_csv(output_all_data, index=False, header=False, mode="a") return data_one_stock_num# 数据标准化data_after_stand = g_stock_num.apply(func_stand, time_step=time_step)data_after_stand.dropna(inplace=True)# 将数据转成训练集合的形式g_stock_num = data_after_stand.groupby(by=["stock_num"])# 清空接收路径下的文件,初始化列名g_stock_num.apply(func_train_test_data, time_step=time_step)

输入特征为60 * 6共360个,输出为股票第62天买 第62天卖的收益类别标签。

到此数据已经准备好了。

建立模型

对于分类预测模型,我们可以使用的有很多,同样,好坏都需要对比实验进行验证。不是说大家都在用的模型就是最好。

本文以梯度提升决策树(GBDT)模型为例进行实验。

模型训练

train_x, test_x, train_y, test_y = train_test_split(X_Classification, Y_Classification, test_size=0.3, random_state=42)model=ensemble.GradientBoostingClassifier()time_start = time.time()model.fit(train_x, train_y)time_end1 = time.time()print('train cost', time_end1 - time_start)

模型预测

yy_predict = model.predict(test_x)

输出模型性能指标,看分类结果的准确性。

print("GBR调超参测试集:" " score", model.score(test_x, test_y) )print(classification_report(yy_predict, y_true))

模型优化

上面的模型使用的是sk-learn中的函数进行了调用,模型的超参都使用的是默认的。显然,默认的参数的准确率不一定最高。我们可以通过尝试不同的超参来提升模型的性能。

寻找最优超参的过程是大量机械性重复的工作。我们可以使用sklearn提供的网格化找超参的函数GridSearchCV。

param_grid = {'learning_rate': [0.2, 0.1, 0.05,0.01,0.005], 'max_depth': range(1, 30, 1), 'min_samples_leaf': range(1, 30, 1), 'min_samples_split': [2, 3, 4, 5, 6,7,8,9,10,11,12,13,14,15]}est = ensemble.GradientBoostingClassifier()# this may take awhilegs_cv = GridSearchCV(est, param_grid=param_grid, n_jobs=1).fit( train_x, train_y.astype('int32'))print(gs_cv.best_score_, gs_cv.grid_scores_)# best hyperparameter settingprint(gs_cv.best_params_)

最终,我们一定能够寻找到一个具有一定预测性能模型。

我们可以输入所有股票的最近的60天的基本数据到模型,预测收益类别。来进行股票的筛选。

进一步的展望

1.影响模型的性能的一大因素就是数据。

如果这些数据是合理的,合逻辑的,那么数据量足够大,数据特征足够多一定会大幅的提升模型的预测准确率。

2.时间周期

本文中训练数据是天级别的数据,我们还可以找时间级别更短的小时级别数据,分钟级别数据,甚至时tick级别每一笔成交数据来进行预测。

3.神经网络模型

神经网络模型是一个万能的拟合器,可以拟合出世界中存在的所有规律,当然前提是数据足够多,网络足够大。

人们虽然解释不了,网络背后的含义,但并不影响我们使用模型得到问题的结果。

国内外使用机器的全自动化交易已经数不胜数,能够稳定盈利的也是不在话下。

加油 共勉

家电维修,空调维修,智能锁维修全国报修号码分享:可以直接拔打400-968-1665 全国各大城市均设网点。
赞(0) 打赏
欢迎转载分享:景合财经 » 股票市场预测模型(股票预测模型的搭建)
分享到: 更多 (0)

觉得文章有用就打赏一下文章作者

非常感谢你的打赏,我们将继续给力更多优质内容,让我们一起创建更加美好的网络世界!

支付宝扫一扫打赏

微信扫一扫打赏

-景合财经

在线报修网点查询