这次我们用循环神经网络(RNN, Recurrent Neural Networks)进行回归(Regression),主要用到LSTM RNN层。
import numpy as np
import matplotlib.pyplot as plt
from keras.models import Sequential
from keras.layers import LSTM, TimeDistributed, Dense
from keras.optimizers import Adam #优化器
np.random.seed(42)
BATCH_START = 0
TIME_STEPS = 20 #序列步长为20
BATCH_SIZE = 50 #每次训练的BATCH_SIZE为50
INPUT_SIZE = 1 #输入维度
OUTPUT_SIZE = 1 #输出维度
CELL_SIZE = 20 #LSTM输出维度
LR = 0.001 #学习率
我们使用RNN来求解回归(Regression)问题. 首先生成序列sin(x),对应输出数据为cos(x),设置序列步长为20,每次训练的BATCH_SIZE为50
def get_batch():
global BATCH_START, TIME_STEPS
xs = np.arange(BATCH_START,BATCH_START+TIME_STEPS*BATCH_SIZE).reshape((BATCH_SIZE,TIME_STEPS)) / (10*np.pi)
seq = np.sin(xs)
res = np.cos(xs)
BATCH_START += TIME_STEPS
#plt.plot(xs[0, :], res[0, :], 'r', xs[0, :], seq[0, :], 'b--')
#plt.show()
return [seq[:,:,np.newaxis],res[:,:,np.newaxis],xs]
然后添加LSTM RNN层,输入为训练数据,输出数据大小由CELL_SIZE定义。因为每一个输入都对应一个输出,所以return_sequences=True。 每一个点的当前输出都受前面所有输出的影响,BATCH之间的参数也需要记忆,故stateful=True
最后添加输出层,LSTM层的每一步都有输出,使用TimeDistributed函数。
model = Sequential() #用于一层一层搭建网络
model.add(LSTM( #添加LSTM RNN层
batch_input_shape = (BATCH_SIZE,TIME_STEPS,INPUT_SIZE),
output_dim = CELL_SIZE, #输出数据大小
return_sequences = True, #每一个输入都对应一个输出,所以return_sequences=True
stateful = True #每一个点的当前输出都受前面所有输出的影响,BATCH之间的参数也需要记忆,故stateful=True
))
model.add(TimeDistributed(Dense(OUTPUT_SIZE))) #LSTM层的每一步都有输出,使用TimeDistributed函数
adam = Adam(LR)
model.compile(optimizer=adam,
loss = 'mse')
print('Training...............')
for step in range(1000):
X_batch, Y_batch, xs = get_batch()
cost = model.train_on_batch(X_batch,Y_batch)
pred = model.predict(X_batch,BATCH_SIZE)
plt.plot(xs[0,:],Y_batch[0].flatten(),'r+',xs[0,:],pred.flatten()[:TIME_STEPS],'b--')
plt.ylim(-1.2,1.2)
plt.draw()
plt.pause(0.1)
if step%50==0:
print('train cost:',cost)
设置优化方法,loss函数和metrics方法之后就可以开始训练了。 训练1000次,调用matplotlib函数采用动画的方式输出结果。