"""
Created on Wed Dec 19 21:02:24 2018
@author: 87671
"""
'''
Univariate LSTM Models(只有一个时间序列)
参考链接:https://machinelearningmastery.com/how-to-develop-lstm-models-for-time-series-forecasting/
'''
# 定义切割函数
from numpy import array
def split_sequence(sequence,n_steps):
X,y = list(),list()
for i in range(len(sequence)):
end_ix = i + n_steps # 也就是y
if end_ix > len(sequence)-1:
break
seq_x, seq_y = sequence[i:end_ix],sequence[end_ix]
X.append(seq_x)
y.append(seq_y)
return array(X),array(y)
#举例
raw_seq=[10,20,30,40,50,60,70,80,90]
n_steps = 3
X,y = split_sequence(raw_seq,n_steps)
for i in range(len(X)):
print(X[i],y[i])
'''
结果如下,也就是想用前3步的信息去预测后一步的信息
[10 20 30] 40
[20 30 40] 50
[30 40 50] 60
[40 50 60] 70
[50 60 70] 80
[60 70 80] 90
'''
# 编译
from keras.models import Sequential
from keras.layers import LSTM
from keras.layers import Dense
###########################################第一个没有任何累加的LSTM
n_features = 1
X = X.reshape((X.shape[0],X.shape[1],n_features)) # 转换成(样本量,时间步,数据维度)
model = Sequential()
model.add(LSTM(50, activation='relu', input_shape=(n_steps, n_features))) # n_features=1,因为是单变量
model.add(Dense(1))
model.compile(optimizer='adam',loss='mse')
model.fit(X,y,epochs=200,verbose=0)
# 预测
x_input = array([70,80,90])
x_input = x_input.reshape((1,n_steps,n_features))
yhat = model.predict(x_input,verbose=0)
print(yhat) # 101.529
##########################################累加一层的LSTM return_sequences=True
model = Sequential()
model.add(LSTM(50, activation='relu', return_sequences=True, input_shape=(n_steps, n_features)))
model.add(LSTM(50, activation='relu'))
model.add(Dense(1))
model.compile(optimizer='adam', loss='mse')
# fit model
model.fit(X, y, epochs=200, verbose=0)
# demonstrate prediction
x_input = array([70, 80, 90])
x_input = x_input.reshape((1, n_steps, n_features))
yhat = model.predict(x_input, verbose=0)
print(yhat) # 103.504944
#########################################双向LSTM(利用的前后的信息去学习)
from keras.layers import Bidirectional
model = Sequential()
model.add(Bidirectional(LSTM(50, activation='relu'), input_shape=(n_steps, n_features)))
model.add(Dense(1))
model.compile(optimizer='adam', loss='mse')
# fit model
model.fit(X, y, epochs=200, verbose=0)
# demonstrate prediction
x_input = array([70, 80, 90])
x_input = x_input.reshape((1, n_steps, n_features))
yhat = model.predict(x_input, verbose=0)
print(yhat)
##########################################CNN+LSTM
from keras.layers import Flatten
from keras.layers import TimeDistributed
from keras.layers.convolutional import Conv1D
from keras.layers.convolutional import MaxPooling1D
raw_seq = [10, 20, 30, 40, 50, 60, 70, 80, 90]
n_steps = 4
X, y = split_sequence(raw_seq, n_steps)
#因为这里要用CNN所以要想像成图片那种二维的格式当做输入,这里每个样本变成了2*2的图片
# reshape from [samples, timesteps] into [samples, subsequences, timesteps, features]
n_features = 1
n_seq = 2
n_steps = 2
X = X.reshape((X.shape[0], n_seq, n_steps, n_features))
print(X.shape) #(5,2,2,1)
# define model
model = Sequential()
model.add(TimeDistributed(Conv1D(filters=64, kernel_size=1, activation='relu'), input_shape=(None, n_steps, n_features)))
model.add(TimeDistributed(MaxPooling1D(pool_size=2)))
model.add(TimeDistributed(Flatten()))
model.add(LSTM(50, activation='relu'))
model.add(Dense(1))
model.compile(optimizer='adam', loss='mse')
# fit model
model.fit(X, y, epochs=500, verbose=0)
# demonstrate prediction
x_input = array([60, 70, 80, 90])
x_input = x_input.reshape((1, n_seq, n_steps, n_features))
yhat = model.predict(x_input, verbose=0)
print(yhat) #102.6211
###########################################convLSTM
# reshape from [samples, timesteps] into [samples, timesteps, rows, columns, features]
n_features = 1
n_seq = 2
n_steps = 2
X = X.reshape((X.shape[0], n_seq, 1, n_steps, n_features))
# define model
model = Sequential()
model.add(ConvLSTM2D(filters=64, kernel_size=(1,2), activation='relu', input_shape=(n_seq, 1, n_steps, n_features)))
model.add(Flatten())
model.add(Dense(1))
model.compile(optimizer='adam', loss='mse')
# fit model
model.fit(X, y, epochs=500, verbose=0)
# demonstrate prediction
x_input = array([60, 70, 80, 90])
x_input = x_input.reshape((1, n_seq, 1, n_steps, n_features))
yhat = model.predict(x_input, verbose=0)
print(yhat)