用Python结合人工智能尝试预测股票,会成就下一个股神?
预备条件:
假设您熟悉python,并且已经在系统中安装了python 3。本教程中使用了jupyter笔记本。您可以使用自己喜欢的IDE。
使用的数据集:
本教程中使用的数据集是基于Tushare获取的股票信息。更多股票代码可以用下面的搜索工具获取。
安装所需的库
对于此项目,您需要在python中安装以下软件包。如果未安装,则只需使用即可pip install PackageName。
- NumPy —该库提供快速计算的n维数组对象。
- Pandas —它提供了一个数据框和序列,可以对数据执行操作和分析。
- matplotlib —该库有助于使用各种图表来可视化数据。
- scikit-learn —这是一个机器学习库,提供了用于预测分析的各种工具和算法。我们将使用其工具或功能进行数据预处理。
- Keras —这是一个基于TensorFlow的高级深度学习库,用于提供神经网络的简单实现。我们之所以使用它,是因为它对初学者友好且易于实施。
- TensorFlow -这个库是由所需Keras作为Keras运行在TensorFlow本身。
开始编码
首先,需要导入将在项目中使用的库。在这里,numpy用于创建NumPy数组以训练和测试数据。pandas用于制作数据集的数据框并轻松检索值。matplotlib.pyplot绘制总体股价和预测价格之类的数据。MinMaxScaler从sklearn的(scikit-learn)预处理程序包中进行归一化处理。Sequential dense LSTM Dropout从Keras导入了数据,将有助于创建深度学习模型。稍后将讨论这些模块。
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.preprocessing import MinMaxScaler
#for deep learning model
from keras import Sequential
from keras.layers import Dense
from keras.layers import LSTM
from keras.layers import Dropout
现在,将数据集作为数据框加载到名为df的变量中。然后,检查了数据集的形状,结果为(2035,8)表示数据集中有2035行和8列。之后,将数据集上下颠倒过来,以便日期从最早的日期开始到最近的日期,这样做还必须重置索引。然后,打印数据集的一些开始行head()。
df = pd.read_csv('tu.csv')
df.shape
df = df[::-1]
df = df.reset_index(drop=True)
df.head()
数据集的前5个条目
仅选择了一个“ 开放”功能来训练的模型,但是您可以自由选择多个功能,但是随后将相应地更改代码。在训练集中,有2000个值,而在测试中,只选择35个值。然后简单地打印了两个类别的数据,分别train_set test_set是(2000,1)和(35,1)。
open_price = df.iloc[:,1:2]
train_set = open_price[:2000].values
test_set = open_price[2000:].values
print("Train size: ",train_set.shape)
print("Test size:",test_set.shape)
在这里,将Date列转换为DateTime格式以方便地进行绘制。然后简单地用于plot_date绘制整个时间轴上的股票开盘价的图,并使用保存该图savefig。
dates = pd.to_datetime(df['Date'])
plt.plot_date(dates, open_price,fmt='-')
plt.savefig("test1final.png")
现在,已经初始化了MinMaxScalar用于缩放0到1范围内的每个值的。这是非常重要的一步,因为当特征处于相对相似的缩放比例时,神经网络和其他算法的收敛速度更快。
sc = MinMaxScaler()
train_set_scaled = sc.fit_transform(train_set)
棘手的部分到了。现在,必须使数据适合我们的RNN模型,即使用目标最终值制作数据序列。让我用这个例子来解释。假设数据集的值介于1到10之间,并且序列长度为3。在这种情况下,训练数据如下所示:
序列训练数据示例
在代码中,序列的长度为60,这意味着只有前60个值将决定下一个值,而不是整个数据集。之后,创建了NumPy x_train和NumPy数组以y_train进行快速计算,并根据模型的要求重塑了训练集。的最终形状为x_train(1940,60,1)。
x_train = []
y_train = []
for i in range(60,2000):
x_train.append(train_set_scaled[i-60:i,0])
y_train.append(train_set_scaled[i,0])
x_train = np.array(x_train)
y_train = np.array(y_train)x_train = np.reshape(x_train,(x_train.shape[0],x_train.shape[1],1))
x_train.shape
现在,将创建模型的架构。使用Keras是因为与其他可用库相比,使用Keras进行深度学习模型非常容易。在这里,初始化了Sequential对象,该对象充当模型内所有图层的捆绑程序。模型总共有4个LSTM层和1个致密层。
LSTM(长期短期记忆)是一种递归神经网络,具有一些上下文状态单元,它们充当长期或短期记忆单元,并且这些单元调节输出。当需要根据历史背景而不是仅根据最后的输入来预测输出时,这一点很重要。例如,必须预测序列3,4,5 ,?中的下一个数字。那么输出就是6(x + 1),但是顺序为0,2,4 ,? 输出也是6,但是它也取决于上下文信息。
Dropout用于通过一次简单地停用某些单元(神经元)来防止数据过拟合。在案例中,一次会停用20%的单元。最后,有一个包含1个单位的密集层,可提供预测值。
然后,只需使用优化程序编译模型,然后将模型拟合到数据上,然后运行20次迭代即可。
reg = Sequential()reg.add(LSTM(units = 50,return_sequences=True,input_shape=(x_train.shape[1],1)))
reg.add(Dropout(0.2))reg.add(LSTM(units = 50,return_sequences=True))
reg.add(Dropout(0.2))reg.add(LSTM(units = 50,return_sequences=True))
reg.add(Dropout(0.2))reg.add(LSTM(units=50))
reg.add(Dropout(0.2))reg.add(Dense(units=1))
reg.compile(optimizer = 'adam',loss='mean_squared_error')
reg.fit(x_train,y_train, epochs=20, batch_size =1,verbose=2)
每次迭代的损失
如您所见,模型收敛于15 个epoch,总共花了90分钟才能运行20次。是的,RNN模型需要时间训练。
RNN模型需要时间
现在,是时候为测试创建输入了。的形状input为(95,1),下面也缩放了此数据。
input = open_price[len(open_price)-len(test_set)-60:].values
input.shape
input = sc.transform(input)
这是最后一部分,其中简单地制作数据序列以预测最近35天的库存值。第一个序列包含从1至60的数据来预测第61个值,第二个序列包含从2到61的数据来预测第62个值,依此类推。的形状x_test是(35,60,1),这说明了这一点。
x_test = []
for i in range(60,95):
x_test.append(input[i-60:i,0])
x_test = np.array(x_test)
x_test = np.reshape(x_test,(x_test.shape[0],x_test.shape[1],1))
x_test.shape
最终,只是预测使用值predict定义的模型的功能,并绘制最后35个某种给定股票的实际和预测值。
pred = reg.predict(x_test)
pred = sc.inverse_transform(pred)
plt.plot(test_set,color='green')
plt.plot(pred,color='red')
plt.title('股票预测')
plt.show()
最后具体运行结果就作为作业留给大家自行完成。但可以很乐观的告诉大家,模型在某些特定时间段上预测给定股票的未来趋势方面非常准确。
但是,距离成为股票市场上的出色顾问还会有比较大的挑战。
下一步目标
通过合并更多功能,增加数据集以及调整模型本身,可以进一步改善模型。