Tensorflow构建RNN做时间序列预测(一)

 

最近比较空闲,刚好学习下Tensorflow和python,于是想写一个Tensorflow的小应用。

时间序列预测在预估企业营收,指标等方面使用的非常多。以前用R写过一个shiny的应用,就是用指数平滑、stl分解等方法做时间序列预测。RNN也是很早之前就接触过理论,是用来处理序列数据的利器。放一个普通RNN的示意图:

 

可以看到,t时刻RNN单元的输出是由t-1时刻单元的输出St-1和t时刻的训练数据xt共同决定的,用公式表示就是St=f(U*Xt+W*S(t−1))

现在比较常用的RNN单元是LSTM、GRU这些,上面那个原始的RNN使用不太多。为什么呢?

从直观的理解来看:1,原始的RNN记忆容量有限,随着时间间隔不断增大时,RNN会丧失学习到远处单元信息的能力。2,原始RNN是全盘接受了输入的信息,但有的信息可能是无用的。于是针对原始RNN的缺点发展出了LSTM——长短期记忆网络。先放一张它的结构示意图:

 

 

 

通常把LSTM单元成为细胞。LSTM使用”门“来选择性的让信息通过,遗忘或增加到细胞状态。还增加了长期记忆机制,就是图中细胞上面的那条横线。LSTM具体的工作原理可以参考这个讲的很详细点击打开链接

Tensorflow中使用的需要关注的是LSTM的输入输出。输入就是训练数据(x,y)。LSTM的输出有两个h、ch是真正的输出状态用来做后续的预测等等,c是细胞的记忆状态。

不说太多理论,直接上代码吧。这边训练数据使用的sin函数产生1000个点,time_step=5

 

1, 生成训练数据

import numpy as np
import pandas as pd
import tensorflow as tf
from tensorflow.contrib import layers as tflayers

def generator(x):
    return [np.sin(i*0.06) for i in range(x)]

def rnn_data_format(data,timestep=7,label=False):
    data=pd.DataFrame(data)
    rnn_data=[]
    if label:  ###label是二维数组,[样本数,1]
        for i in range(len(data) - timestep):
           rnn_data.append([x for x in data.iloc[i+timestep].as_matrix()])
    else:     ###样本是3维数组[样本数,time_step,1]
        for i in range(len(data) - timestep):
           rnn_data.append([x for x in data.iloc[i:(i+timestep)].as_matrix()])
    return np.array(rnn_data,dtype=np.float32)
class DataSet(object):
    def __init__(self, x,y):
        self._data_size = len(x)
        self._epochs_completed = 0
        self._index_in_epoch = 0
        self._data_index = np.arange(len(x))
        self.x=x
        self.y=y

    def next_batch(self,batch_size):
        start=self._index_in_epoch
        if start+batch_size>=self._data_size :
            np.random.shuffle(self._data_index)
            self._index_in_epoch=0
            start=self._index_in_epoch
            end=self._index_in_epoch+batch_size
            self._index_in_epoch=end
        else:
            end = self._index_in_epoch + batch_size
            self._index_in_epoch = end
        batch_x,batch_y=self.get_data(start,end)
        return np.array(batch_x,dtype=np.float32),np.array(batch_y,dtype=np.float32)

    def get_data(self,start,end):
        batch_x=[]
        batch_y=[]
        for i in range(start,end):
            batch_x.append(self.x[self._data_index[i]])
            batch_y.append(self.y[self._data_index[i]])
        return batch_x,batch_y

##生成数据
x=generator(1000)
X=rnn_data_format(x,5)
y=rnn_data_format(x,5,label=True)
trainds = DataSet(X,y)

上面的代码用来生产训练数据,用sin函数生成了1000个数据点。rnn_data_format是为了生成[time_step, input]维度的数据。这里吧time_step设为5。因此可知,X的每一个样本是shape为[5,1]的矩阵,用来预测y,y的每一个样本shape为[1,1]。

 

  • 18
    点赞
  • 131
    收藏
    觉得还不错? 一键收藏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值