精华内容
下载资源
问答
  • 循环神经网络学习流量预测lstm适用于初学者学习使用
  • 完整代码,可直接运行
  • 循环神经网络学习流量预测lstm适用于初学者学习使用
  • 循环神经网络预测,循环神经网络预测天气代码,Python源码.rar
  • 循环神经网络预测,循环神经网络预测天气代码,Python源码.zip
  • 使用循环神经网络预测温度

    千次阅读 2020-12-31 21:42:03
    本文以天气时间序列数据集为例,讨论如何使用深度学习模型预测未来天气温度。 使用的是由德国耶拿马克思普朗克生物地球化学研究所的气象站记录。 数据每10分钟记录一次,共记录14种不同的量,如气温、气压、湿度、...

    简介


    本文以天气时间序列数据集为例,讨论如何使用深度学习模型预测未来天气温度。

    使用的是由德国耶拿马克思普朗克生物地球化学研究所的气象站记录。

    数据每10分钟记录一次,共记录14种不同的量,如气温、气压、湿度、风向等,原始数据可追溯到2003年,本例只使用2009-2016年的数据。

    数据


    下载并解压数据略。

    加载数据:

    data_dir = r'E:\practice\tf2\temperature'
    fname = os.path.join(data_dir, 'jena_climate_2009_2016.csv')
    
    f = open(fname)
    data = f.read()
    f.close()
    
    lines = data.split('\n')
    header = lines[0].split(',')
    lines = lines[1:]
    	
    print(header)
    print(len(lines))
    

    如下图:

    在这里插入图片描述

    查看温度:

    # 解析数据到Numpy向量
    import numpy as np
    float_data = np.zeros((len(lines), len(header) - 1))
    for i, line in enumerate(lines):
    	values = [float(x) for x in line.split(',')[1:]]
    	float_data[i, :] = values
    
    # 查看温度序列
    from matplotlib import pyplot as plt
    
    temp = float_data[:, 1]
    plt.plot(range(len(temp)), temp)
    plt.title('All days temperature')
    plt.legend()
    plt.figure()
    
    # 全部的数据不容易看清楚,查看前10天的数据
    plt.plot(range(1440), temp[:1440])
    plt.title('First 10 days temperature')
    plt.legend()
    plt.show()
    

    如下图:

    在这里插入图片描述

    准备数据


    用数学语言重新描述一下问题:

    一个时间步是10分钟,每个steps有一个数据点,给定过去lookback个时间步之内的数据,预测delay个时间步之后的温度。

    假定:

    • lookback = 720,即给定过去5天内的数据
    • steps = 6,即采样频率1小时
    • delay = 144,即预测未来24小时后的温度

    开始数据预处理:

    # 数据标准化
    mean = float_data[:200000].mean(axis = 0)
    float_data -= mean
    std = float_data[:200000].std(axis = 0)
    float_data /= std
    

    由于数据集中样本高度冗余,编写一个数据生成器,使用原始数据即时生成样本:

    # 生成器:生成时间序列样本及其目标
    def generator(data, lookback, delay, min_index, max_index, shuffle = False, batch_size = 128, step = 6):
    	if max_index is None:
    		max_index = len(data) - delay - 1
    	i = min_index + lookback
    	while 1:
    		if shuffle:
    			rows = np.random.randint(min_index + lookback, max_index, size = batch_size)
    		else:
    			if i + batch_size >= max_index:
    				i = min_index + lookback
    			rows = np.arange(i, min(i + batch_size, max_index))
    			i += len(rows)
    		
    		samples = np.zeros((len(rows), lookback // step, data.shape[-1]))
    		targets = np.zeros((len(rows), ))
    		for j, row in enumerate(rows):
    			indices = range(rows[j] - lookback, rows[j], step)
    			samples[j] = data[indices]
    			targets[j] = data[rows[j] + delay][1]
    		yield samples, targets
    

    各参数说明如下:

    • data: 浮点数组成的原始数组
    • lookback: 输入数据应该包括过去多少个时间步
    • delay: 目标应该在未来多少个时间步之后
    • min_index和max_index:data数组中的索引,用于界定需要抽取哪些时间步。这有助于保存一部分数据用于验证,另一部分用于测试
    • shuffle: 是否打乱样本
    • batch_size;批量样本数量
    • step:数据采样周期,设置为6,表示每小时取样一次

    输出为(samples, targets)无组,其中,samples是输入数据中的一个批量,targets是对应的目标温度数组。

    使用上述函数准备训练生成器、验证生成器和测试生成器:

    lookback = 1440
    step = 6
    delay = 144
    batch_size = 128
    
    train_gen = generator(float_data, lookback = lookback, delay = delay, min_index = 0, max_index = 200000, shuffle = True, step = step, batch_size = batch_size)
    val_gen = generator(float_data, lookback = lookback, delay = delay, min_index = 200001, max_index = 300000, step = step, batch_size = batch_size)
    train_gen = generator(float_data, lookback = lookback, delay = delay, min_index = 300001, max_index = None, step = step, batch_size = batch_size)
    
    val_steps = (300000 - 200001 - lookback) // batch_size
    test_steps = (len(float_data) - 300001 - lookback) // batch_size
    

    建立最低基准


    在进行机器学习预测温度之前,我们最好有一个最低的标准,这样才能更好地评估模型预测的结果是否靠谱。

    最低基准,应该就是通过常识得到的预测。对于温度,我们有理由预测未来24小时的温度与当前温度相同。

    评估一下:

    # 对比基准,基于常识的预测结果
    def evaluate_native_method():
    	batch_maes = []
    	for step in range(val_steps):
    		samples, targets = next(val_gen)
    		preds = samples[:, -1, 1]
    		mae = np.mean(np.abs(preds - targets))
    		batch_maes.append(mae)
    	print(np.mean(batch_maes))
    		
    evaluate_native_method()
    celsius_mae = 0.29 * std[1]
    print(celsius_mae)
    

    在这里插入图片描述

    得到MAE为0.29。把它转化为温度的平均绝对误差,为2.57度。

    下面看看深度学习模型能不能把这个误差减小。

    密集连接模型


    在开始一项深度学习研究时,常常会使用简单的模型对问题先进行处理,再进行较为复杂的模型研究。

    而密集连接模型较为简单,且计算代价不高,可以直接搞起:

    # 首先使用简单的密集连接网络进行预测
    from keras.models import Sequential
    from keras import layers
    from keras.optimizers import RMSprop
    
    model = Sequential()
    model.add(layers.Flatten(input_shape = (lookback // step, float_data.shape[-1])))
    model.add(layers.Dense(32, activation = 'relu'))
    model.add(layers.Dense(1))
    
    model.compile(optimizer = RMSprop(), loss = 'mae')
    history = model.fit_generator(train_gen, steps_per_epoch = 500, epochs = 20, validation_data = val_gen, validation_steps = val_steps)
    
    # 绘图
    import matplotlib.pyplot as plt
    
    loss = history.history['loss']
    val_loss = history.history['val_loss']
    
    epochs = range(1, len(loss) + 1)
    
    plt.figure()
    
    plt.plot(epochs, loss, 'bo', label = 'Training loss')
    plt.plot(epochs, val_loss, 'b', label = 'Validation loss')
    plt.title('Training and Validation loss')
    
    plt.legend()
    plt.show()
    

    结果如下:

    在这里插入图片描述

    可见,这个预测结果并不可靠,战胜常识得到的最低基准并不容易。

    常识是一个很简单的模型,使用深度学习的复杂框架却学习不到这个模型,这也是深度学习存在的一个问题。

    使用循环网络


    基于温度数据的预测,是有序的数据。拿3个月前的数据来预测明天的温度,差别就会很大。

    而密集连接网络把时间序列展开,就删除了时间序列的概念。

    使用循环网络的GRU层可以以较低的计算低价把时间序列引入到预测中去:

    # 基于GRU的模型
    from keras.models import Sequential
    from keras import layers
    from keras.optimizers import RMSprop
    
    model = Sequential()
    model.add(layers.GRU(32, input_shape = (None, float_data.shape[-1])))
    model.add(layers.Dense(1))
    
    model.compile(optimizer = RMSprop(), loss = 'mae')
    history = model.fit_generator(train_gen, steps_per_epoch = 500, epochs = 20, validation_data = val_gen, validation_steps = val_steps)
    
    # 绘图
    import matplotlib.pyplot as plt
    
    loss = history.history['loss']
    val_loss = history.history['val_loss']
    
    epochs = range(1, len(loss) + 1)
    
    plt.figure()
    
    plt.plot(epochs, loss, 'bo', label = 'Training loss')
    plt.plot(epochs, val_loss, 'b', label = 'Validation loss')
    plt.title('Training and Validation loss')
    
    plt.legend()
    plt.show()
    

    结果有所提高,但过拟合却较严重,还有提升空间。

    使用循环dropout降低过拟合


    dropout,就是将某一层的输入单元随机设置为0,目的是打破该层训练数据中的偶然相关性。

    keras每个循环层都有两个与dropout相关的参数:

    • dropout: 浮点数,指定该层输入单元的dropout比率
    • recurrent_dropout: 指定循环单元的dropout比率

    注意,添加dropout后,网络需要更长的时间才能完全收敛,所以网络训练轮次增加为原先的2倍。

    如下:

    # 使用循环dropout降低过拟合
    model = Sequential()
    model.add(layers.GRU(32, dropout = 0.2, recurrent_dropout = 0.2, input_shape = (None, float_data.shape[-1])))
    model.add(layers.Dense(1))
    
    model.compile(optimizer = RMSprop(), loss = 'mae')
    history = model.fit_generator(train_gen, steps_per_epoch = 500, epochs = 40, validation_data = val_gen, validation_steps = val_steps)
    
    # 绘图
    import matplotlib.pyplot as plt
    
    loss = history.history['loss']
    val_loss = history.history['val_loss']
    
    epochs = range(1, len(loss) + 1)
    
    plt.figure()
    
    plt.plot(epochs, loss, 'bo', label = 'Training loss')
    plt.plot(epochs, val_loss, 'b', label = 'Validation loss')
    plt.title('Training and Validation loss')
    
    plt.legend()
    plt.show()
    

    过拟合大大降低了,预测结果也更加稳定,但效果并没有好很多。

    循环层堆叠


    模型不再过拟合,但似乎遇到了性能瓶颈,可以考虑增加网络容量。

    增加网络容量的通常做法是增加每层单元数或增加层数。循环层堆叠是构建更加强大网络的经典方法。

    如下:

    # 堆叠GRU模型
    model = Sequential()
    model.add(layers.GRU(32, dropout = 0.1, recurrent_dropout = 0.5, return_sequences = True, input_shape = (None, float_data.shape[-1])))
    model.add(layers.GRU(64, activation = 'relu', dropout = 0.1, recurrent_dropout = 0.5))
    model.add(layers.Dense(1))
    
    model.compile(optimizer = RMSprop(), loss = 'mae')
    history = model.fit_generator(train_gen, steps_per_epoch = 500, epochs = 40, validation_data = val_gen, validation_steps = val_steps)
    
    # 绘图
    import matplotlib.pyplot as plt
    
    loss = history.history['loss']
    val_loss = history.history['val_loss']
    
    epochs = range(1, len(loss) + 1)
    
    plt.figure()
    
    plt.plot(epochs, loss, 'bo', label = 'Training loss')
    plt.plot(epochs, val_loss, 'b', label = 'Validation loss')
    plt.title('Training and Validation loss')
    
    plt.legend()
    plt.show()
    

    结果有所改进,但并不显著。过拟合并不严重,还可以增加网络容量。但添加网络容量对于效果的影响并不会线性增加。

    使用双向RNN


    RNN是按顺序处理输入序列的时间步,而打乱或反转时间步会完全改变RNN从序列中提取的表示。

    双向RNN利用了RNN的顺序敏感性,它包含两个普通的RNN,每个RNN分别沿着一个方向对输入序列进行处理,然后将它们的表示合并在一起。

    通过这样处理,双向RNN能够捕捉到可能被单向RNN忽略的模式。

    代码如下:

    # 使用双向RNN
    model = Sequential()
    model.add(layers.Bidirectional(layers.GRU(32), input_shape = (None, float_data.shape[-1])))
    model.add(layers.Dense(1))
    
    model.compile(optimizer = RMSprop(), loss = 'mae')
    history = model.fit_generator(train_gen, steps_per_epoch = 500, epochs = 40, validation_data = val_gen, validation_steps = val_steps)
    
    # 绘图
    import matplotlib.pyplot as plt
    
    loss = history.history['loss']
    val_loss = history.history['val_loss']
    
    epochs = range(1, len(loss) + 1)
    
    plt.figure()
    
    plt.plot(epochs, loss, 'bo', label = 'Training loss')
    plt.plot(epochs, val_loss, 'b', label = 'Validation loss')
    plt.title('Training and Validation loss')
    
    plt.legend()
    plt.show()
    

    这个模型的表现与普通GRU层差不多,因为所有有效的预测都来自正常顺序的好一半网络。

    毕竟,对于温度预测的问题,反向顺序并不会得到有用的表示。

    对于影评,可能会有较好的表现。因为单词都在那里,反向可能会抓取的信息更多一点。

    小结


    本文展示了处理温度预测问题的整个过程。

    对问题分析、数据处理、基准建立、模型应用、模型改进、过拟合等过程进行了描述。

    对于本例,还有很多可以优化的工作可以处理,如增大循环层中单元个数、调用优化器学习率等。

    参考资料

    《Python深度学习》

    展开全文
  • 循环神经网络预测,循环神经网络预测天气代码,Python源码.zip.zip
  • 将神经网络模型训练好之后,在输入层给定一个x,通过网络之后就能够在输出层得到特定的y,那么既然有了这么强大的模型,为什么还需要RNN(循环神经网络)呢? 1 为什么需要RNN(循环神经网络) 他们都只能单独的取...

    一、获取代码方式

    获取代码方式1:
    完整代码已上传我的资源:【预测模型】基于matlab RNN循环神经网络预测【含Matlab源码 363期】

    获取代码方式2:
    通过订阅紫极神光博客付费专栏,凭支付凭证,私信博主,可获得此代码。

    备注:
    订阅紫极神光博客付费专栏,可免费获得1份代码(有效期为订阅日起,三天内有效);

    二、RNN循环神经网络简介

    神经网络可以当做是能够拟合任意函数的黑盒子,只要训练数据足够,给定特定的x,就能得到希望的y,结构图如下:
    在这里插入图片描述
    将神经网络模型训练好之后,在输入层给定一个x,通过网络之后就能够在输出层得到特定的y,那么既然有了这么强大的模型,为什么还需要RNN(循环神经网络)呢?

    1 为什么需要RNN(循环神经网络)
    他们都只能单独的取处理一个个的输入,前一个输入和后一个输入是完全没有关系的。但是,某些任务需要能够更好的处理序列的信息,即前面的输入和后面的输入是有关系的。

    比如,当我们在理解一句话意思时,孤立的理解这句话的每个词是不够的,我们需要处理这些词连接起来的整个序列; 当我们处理视频的时候,我们也不能只单独的去分析每一帧,而要分析这些帧连接起来的整个序列。
    以nlp的一个最简单词性标注任务来说,将我 吃 苹果 三个单词标注词性为 我/nn 吃/v 苹果/nn。
    那么这个任务的输入就是:
    我 吃 苹果 (已经分词好的句子)
    这个任务的输出是:
    我/nn 吃/v 苹果/nn(词性标注好的句子)
    对于这个任务来说,我们当然可以直接用普通的神经网络来做,给网络的训练数据格式了就是我-> 我/nn 这样的多个单独的单词->词性标注好的单词。
    但是很明显,一个句子中,前一个单词其实对于当前单词的词性预测是有很大影响的,比如预测苹果的时候,由于前面的吃是一个动词,那么很显然苹果作为名词的概率就会远大于动词的概率,因为动词后面接名词很常见,而动词后面接动词很少见。
    所以为了解决一些这样类似的问题,能够更好的处理序列的信息,RNN就诞生了。
    2 RNN结构
    首先看一个简单的循环神经网络如,它由输入层、一个隐藏层和一个输出层组成:
    在这里插入图片描述
    不知道初学的同学能够理解这个图吗,反正我刚开始学习的时候是懵逼的,每个结点到底代表的是一个值的输入,还是说一层的向量结点集合,如何隐藏层又可以连接到自己,等等这些疑惑~这个图是一个比较抽象的图。
    我们现在这样来理解,如果把上面有W的那个带箭头的圈去掉,它就变成了最普通的全连接神经网络。x是一个向量,它表示输入层的值(这里面没有画出来表示神经元节点的圆圈);s是一个向量,它表示隐藏层的值(这里隐藏层面画了一个节点,你也可以想象这一层其实是多个节点,节点数与向量s的维度相同);
    U是输入层到隐藏层的权重矩阵,o也是一个向量,它表示输出层的值;V是隐藏层到输出层的权重矩阵。
    那么,现在我们来看看W是什么。循环神经网络的隐藏层的值s不仅仅取决于当前这次的输入x,还取决于上一次隐藏层的值s。权重矩阵 W就是隐藏层上一次的值作为这一次的输入的权重。
    我们给出这个抽象图对应的具体图:
    在这里插入图片描述
    我们从上图就能够很清楚的看到,上一时刻的隐藏层是如何影响当前时刻的隐藏层的。
    如果我们把上面的图展开,循环神经网络也可以画成下面这个样子:
    在这里插入图片描述
    在这里插入图片描述
    3 总结
    好了,到这里大概讲解了RNN最基本的几个知识点,能够帮助大家直观的感受RNN和了解为什么需要RNN,后续总结它的反向求导知识点。
    最后给出RNN的总括图:
    在这里插入图片描述

    三、部分源代码

    clc;
    clear all;
    [train_data,test_data]=LSTM_data_process();  
    data_length=size(train_data,1);  
    data_num=size(train_data,2);  
    %% 网络参数初始化  
    % 结点数设置  
    input_num=data_length;  
    cell_num=5;  
    output_num=size(test_data,1);  
    % 网络中门的偏置  
    bias_input_gate=rand(1,cell_num);  
    bias_forget_gate=rand(1,cell_num);  
    bias_output_gate=rand(1,cell_num);  
    %网络权重初始化  
    ab=20;  
    weight_input_x=rand(input_num,cell_num)/ab;  
    weight_input_h=rand(output_num,cell_num)/ab;  
    weight_inputgate_x=rand(input_num,cell_num)/ab;  
    weight_inputgate_c=rand(cell_num,cell_num)/ab;  
    weight_forgetgate_x=rand(input_num,cell_num)/ab;  
    weight_forgetgate_c=rand(cell_num,cell_num)/ab;  
    weight_outputgate_x=rand(input_num,cell_num)/ab;  
    weight_outputgate_c=rand(cell_num,cell_num)/ab;  
    %hidden_output权重  
    weight_preh_h=rand(cell_num,output_num);  
    %网络状态初始化  
    cost_gate=0.25;  
    h_state=rand(output_num,data_num);  
    cell_state=rand(cell_num,data_num);  
    %% 网络训练学习  
    for iter=1:100  
        yita=0.01;            %每次迭代权重调整比例  
        for m=1:data_num  
            %前馈部分  
            if(m==1)  
                gate=tanh(train_data(:,m)'*weight_input_x);  
                input_gate_input=train_data(:,m)'*weight_inputgate_x+bias_input_gate;  
                output_gate_input=train_data(:,m)'*weight_outputgate_x+bias_output_gate;  
                for n=1:cell_num  
                    input_gate(1,n)=1/(1+exp(-input_gate_input(1,n)));  
                    output_gate(1,n)=1/(1+exp(-output_gate_input(1,n)));  
                end  
                forget_gate=zeros(1,cell_num);  
                forget_gate_input=zeros(1,cell_num);  
                cell_state(:,m)=(input_gate.*gate)';  
            else  
                gate=tanh(train_data(:,m)'*weight_input_x+h_state(:,m-1)'*weight_input_h);  
                input_gate_input=train_data(:,m)'*weight_inputgate_x+cell_state(:,m-1)'*weight_inputgate_c+bias_input_gate;  
                forget_gate_input=train_data(:,m)'*weight_forgetgate_x+cell_state(:,m-1)'*weight_forgetgate_c+bias_forget_gate;  
                output_gate_input=train_data(:,m)'*weight_outputgate_x+cell_state(:,m-1)'*weight_outputgate_c+bias_output_gate;  
                for n=1:cell_num  
                    input_gate(1,n)=1/(1+exp(-input_gate_input(1,n)));  
                    forget_gate(1,n)=1/(1+exp(-forget_gate_input(1,n)));  
                    output_gate(1,n)=1/(1+exp(-output_gate_input(1,n)));  
                end  
                cell_state(:,m)=(input_gate.*gate+cell_state(:,m-1)'.*forget_gate)';     
            end  
            pre_h_state=tanh(cell_state(:,m)').*output_gate;  
            h_state(:,m)=(pre_h_state*weight_preh_h)';   
        end  
        % 误差的计算  
        Error=h_state(:,m)-train_data(:,m);  
    %     Error=h_state(:,:)-train_data(end,:);  
        Error_Cost(1,iter)=sum(Error.^2);  
        if Error_Cost(1,iter) < cost_gate  
                iter  
            break;  
        end  
                    [ weight_input_x,...  
                    weight_input_h,...  
                    weight_inputgate_x,...  
                    weight_inputgate_c,...  
                    weight_forgetgate_x,...  
                    weight_forgetgate_c,...  
                    weight_outputgate_x,...  
                    weight_outputgate_c,...  
                    weight_preh_h ]=LSTM_updata_weight(m,yita,Error,...  
                                                       weight_input_x,...  
                                                       weight_input_h,...  
                                                       weight_inputgate_x,...  
                                                       weight_inputgate_c,...  
                                                       weight_forgetgate_x,...  
                                                       weight_forgetgate_c,...  
                                                       weight_outputgate_x,...  
                                                       weight_outputgate_c,...  
                                                       weight_preh_h,...  
                                                       cell_state,h_state,...  
                                                       input_gate,forget_gate,...  
                                                       output_gate,gate,...  
                                                       train_data,pre_h_state,...  
                                                       input_gate_input,...  
                                                       output_gate_input,...  
                                                       forget_gate_input);  
      
      
    end  
    

    四、运行结果

    在这里插入图片描述

    五、matlab版本及参考文献

    1 matlab版本
    2014a

    2 参考文献
    [1] 包子阳,余继周,杨杉.智能优化算法及其MATLAB实例(第2版)[M].电子工业出版社,2016.
    [2]张岩,吴水根.MATLAB优化算法源代码[M].清华大学出版社,2017.
    [3]周品.MATLAB 神经网络设计与应用[M].清华大学出版社,2013.
    [4]陈明.MATLAB神经网络原理与实例精解[M].清华大学出版社,2013.
    [5]方清城.MATLAB R2016a神经网络设计与应用28个案例分析[M].清华大学出版社,2018.

    展开全文
  • 循环神经网络的python应用代码。可参考。但注释较少,适合一定基础的,下载时请慎重。
  • 网络游戏-基于循环神经网络预测移动用户间相遇概率的方法.zip
  • 循环神经网络

    2021-01-06 22:35:19
    循环神经网络特点:为更好地处理时序信息而设计的。它引⼊状态变量来存储过去的信息,并⽤其与当前的输⼊共同决定当前的输出。 循环神经⽹络常⽤于处理序列数据,如⼀段⽂字或声⾳、购物或观影的顺序,甚⾄是图像中...
  • 今天是第10天,我们将使用LSTM完成股票开盘价格的预测,最后的R2可达到0.74,相对传统的RNN的0.72提高了两个百分点。 我的环境: 语言环境:Python3.6.5 编译器:jupyter notebook 深度学习环境:TensorFlow2.4.1 ...

    本文已加入 🚀 Python AI 计划,从一个Python小白到一个AI大神,你所需要的所有知识都在我的 GitHub:https://github.com/kzbkzb/Python-AI 了。

    一、前言

    今天是第10天,我们将使用LSTM完成股票开盘价格的预测,最后的R2可达到0.74,相对传统的RNN的0.72提高了两个百分点。

    我的环境:

    • 语言环境:Python3.6.5
    • 编译器:jupyter notebook
    • 深度学习环境:TensorFlow2.4.1

    来自专栏:【深度学习100例】

    往期精彩内容:

    如果你还是一名小白,可以看看我这个专门为你写的专栏:《小白入门深度学习》,帮助零基础的你入门深度学习。

    二、LSTM的是什么

    神经网络程序的基本流程
    在这里插入图片描述

    一句话介绍LSTM,它是RNN的进阶版,如果说RNN的最大限度是理解一句话,那么LSTM的最大限度则是理解一段话,详细介绍如下:

    LSTM,全称为长短期记忆网络(Long Short Term Memory networks),是一种特殊的RNN,能够学习到长期依赖关系。LSTM由Hochreiter & Schmidhuber (1997)提出,许多研究者进行了一系列的工作对其改进并使之发扬光大。LSTM在许多问题上效果非常好,现在被广泛使用。

    所有的循环神经网络都有着重复的神经网络模块形成链的形式。在普通的RNN中,重复模块结构非常简单,其结构如下:

    在这里插入图片描述

    LSTM避免了长期依赖的问题。可以记住长期信息!LSTM内部有较为复杂的结构。能通过门控状态来选择调整传输的信息,记住需要长时间记忆的信息,忘记不重要的信息,其结构如下:

    在这里插入图片描述

    三、准备工作

    1.设置GPU

    如果使用的是CPU可以注释掉这部分的代码。

    import tensorflow as tf
    
    gpus = tf.config.list_physical_devices("GPU")
    
    if gpus:
        tf.config.experimental.set_memory_growth(gpus[0], True)  #设置GPU显存用量按需使用
        tf.config.set_visible_devices([gpus[0]],"GPU")
    

    2.设置相关参数

    import pandas            as pd
    import tensorflow        as tf  
    import numpy             as np
    import matplotlib.pyplot as plt
    # 支持中文
    plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签
    plt.rcParams['axes.unicode_minus'] = False  # 用来正常显示负号
    
    from numpy                 import array
    from sklearn               import metrics
    from sklearn.preprocessing import MinMaxScaler
    from keras.models          import Sequential
    from keras.layers          import Dense,LSTM,Bidirectional
    
    
    # 确保结果尽可能重现
    from numpy.random          import seed
    seed(1)
    tf.random.set_seed(1)
    
    # 设置相关参数
    n_timestamp  = 40    # 时间戳
    n_epochs     = 20    # 训练轮数
    # ====================================
    #      选择模型:
    #            1: 单层 LSTM
    #            2: 多层 LSTM
    #            3: 双向 LSTM
    # ====================================
    model_type = 1
    

    3.加载数据

    data = pd.read_csv('./datasets/SH600519.csv')  # 读取股票文件
    
    data
    
    Unnamed: 0dateopenclosehighlowvolumecode
    0742010-04-2688.70287.38189.07287.362107036.13600519
    1752010-04-2787.35584.84187.35584.68158234.48600519
    2762010-04-2884.23584.31885.12883.59726287.43600519
    3772010-04-2984.59285.67186.31584.59234501.20600519
    4782010-04-3083.87182.34083.87181.52385566.70600519
    ...........................
    242124952020-04-201221.0001227.3001231.5001216.80024239.00600519
    242224962020-04-211221.0201200.0001223.9901193.00029224.00600519
    242324972020-04-221206.0001244.5001249.5001202.22044035.00600519
    242424982020-04-231250.0001252.2601265.6801247.77026899.00600519
    242524992020-04-241248.0001250.5601259.8901235.18019122.00600519

    2426 rows × 8 columns

    """
    前(2426-300=2126)天的开盘价作为训练集,后300天的开盘价作为测试集
    """
    training_set = data.iloc[0:2426 - 300, 2:3].values  
    test_set     = data.iloc[2426 - 300:, 2:3].values
    

    四、数据预处理

    1.归一化

    #将数据归一化,范围是0到1
    sc  = MinMaxScaler(feature_range=(0, 1))
    training_set_scaled = sc.fit_transform(training_set)
    testing_set_scaled  = sc.transform(test_set) 
    

    2.时间戳函数

    # 取前 n_timestamp 天的数据为 X;n_timestamp+1天数据为 Y。
    def data_split(sequence, n_timestamp):
        X = []
        y = []
        for i in range(len(sequence)):
            end_ix = i + n_timestamp
            
            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)
    
    X_train, y_train = data_split(training_set_scaled, n_timestamp)
    X_train          = X_train.reshape(X_train.shape[0], X_train.shape[1], 1)
    
    X_test, y_test   = data_split(testing_set_scaled, n_timestamp)
    X_test           = X_test.reshape(X_test.shape[0], X_test.shape[1], 1)
    

    五、构建模型

    # 建构 LSTM模型
    if model_type == 1:
        # 单层 LSTM
        model = Sequential()
        model.add(LSTM(units=50, activation='relu',
                       input_shape=(X_train.shape[1], 1)))
        model.add(Dense(units=1))
    if model_type == 2:
        # 多层 LSTM
        model = Sequential()
        model.add(LSTM(units=50, activation='relu', return_sequences=True,
                       input_shape=(X_train.shape[1], 1)))
        model.add(LSTM(units=50, activation='relu'))
        model.add(Dense(1))
    if model_type == 3:
        # 双向 LSTM
        model = Sequential()
        model.add(Bidirectional(LSTM(50, activation='relu'),
                                input_shape=(X_train.shape[1], 1)))
        model.add(Dense(1))
        
    model.summary() # 输出模型结构
    
    WARNING:tensorflow:Layer lstm will not use cuDNN kernel since it doesn't meet the cuDNN kernel criteria. It will use generic GPU kernel as fallback when running on GPU
    Model: "sequential"
    _________________________________________________________________
    Layer (type)                 Output Shape              Param #   
    =================================================================
    lstm (LSTM)                  (None, 50)                10400     
    _________________________________________________________________
    dense (Dense)                (None, 1)                 51        
    =================================================================
    Total params: 10,451
    Trainable params: 10,451
    Non-trainable params: 0
    _________________________________________________________________
    

    六、激活模型

    # 该应用只观测loss数值,不观测准确率,所以删去metrics选项,一会在每个epoch迭代显示时只显示loss值
    model.compile(optimizer=tf.keras.optimizers.Adam(0.001),
                  loss='mean_squared_error')  # 损失函数用均方误差
    

    七、训练模型

    history = model.fit(X_train, y_train, 
                        batch_size=64, 
                        epochs=n_epochs, 
                        validation_data=(X_test, y_test), 
                        validation_freq=1)                  #测试的epoch间隔数
    
    model.summary()
    
    Epoch 1/20
    33/33 [==============================] - 5s 107ms/step - loss: 0.1049 - val_loss: 0.0569
    Epoch 2/20
    33/33 [==============================] - 3s 86ms/step - loss: 0.0074 - val_loss: 1.1616
    Epoch 3/20
    33/33 [==============================] - 3s 83ms/step - loss: 0.0012 - val_loss: 0.1408
    Epoch 4/20
    33/33 [==============================] - 3s 78ms/step - loss: 5.8758e-04 - val_loss: 0.0421
    Epoch 5/20
    33/33 [==============================] - 3s 84ms/step - loss: 5.3411e-04 - val_loss: 0.0159
    Epoch 6/20
    33/33 [==============================] - 3s 81ms/step - loss: 3.9690e-04 - val_loss: 0.0034
    Epoch 7/20
    33/33 [==============================] - 3s 84ms/step - loss: 4.3521e-04 - val_loss: 0.0032
    Epoch 8/20
    33/33 [==============================] - 3s 85ms/step - loss: 3.8233e-04 - val_loss: 0.0059
    Epoch 9/20
    33/33 [==============================] - 3s 81ms/step - loss: 3.6539e-04 - val_loss: 0.0082
    Epoch 10/20
    33/33 [==============================] - 3s 81ms/step - loss: 3.1790e-04 - val_loss: 0.0141
    Epoch 11/20
    33/33 [==============================] - 3s 82ms/step - loss: 3.5332e-04 - val_loss: 0.0166
    Epoch 12/20
    33/33 [==============================] - 3s 86ms/step - loss: 3.2684e-04 - val_loss: 0.0155
    Epoch 13/20
    33/33 [==============================] - 3s 80ms/step - loss: 2.6495e-04 - val_loss: 0.0149
    Epoch 14/20
    33/33 [==============================] - 3s 84ms/step - loss: 3.1398e-04 - val_loss: 0.0172
    Epoch 15/20
    33/33 [==============================] - 3s 80ms/step - loss: 3.4533e-04 - val_loss: 0.0077
    Epoch 16/20
    33/33 [==============================] - 3s 81ms/step - loss: 2.9621e-04 - val_loss: 0.0082
    Epoch 17/20
    33/33 [==============================] - 3s 83ms/step - loss: 2.2228e-04 - val_loss: 0.0092
    Epoch 18/20
    33/33 [==============================] - 3s 86ms/step - loss: 2.4517e-04 - val_loss: 0.0093
    Epoch 19/20
    33/33 [==============================] - 3s 86ms/step - loss: 2.7179e-04 - val_loss: 0.0053
    Epoch 20/20
    33/33 [==============================] - 3s 82ms/step - loss: 2.5923e-04 - val_loss: 0.0054
    Model: "sequential"
    _________________________________________________________________
    Layer (type)                 Output Shape              Param #   
    =================================================================
    lstm (LSTM)                  (None, 50)                10400     
    _________________________________________________________________
    dense (Dense)                (None, 1)                 51        
    =================================================================
    Total params: 10,451
    Trainable params: 10,451
    Non-trainable params: 0
    _________________________________________________________________
    

    八、结果可视化

    1.绘制loss图

    plt.plot(history.history['loss']    , label='Training Loss')
    plt.plot(history.history['val_loss'], label='Validation Loss')
    plt.title('Training and Validation Loss by K同学啊')
    plt.legend()
    plt.show()
    

    在这里插入图片描述

    2.预测

    predicted_stock_price = model.predict(X_test)                        # 测试集输入模型进行预测
    predicted_stock_price = sc.inverse_transform(predicted_stock_price)  # 对预测数据还原---从(0,1)反归一化到原始范围
    real_stock_price      = sc.inverse_transform(y_test)# 对真实数据还原---从(0,1)反归一化到原始范围
    
    # 画出真实数据和预测数据的对比曲线
    plt.plot(real_stock_price, color='red', label='Stock Price')
    plt.plot(predicted_stock_price, color='blue', label='Predicted Stock Price')
    plt.title('Stock Price Prediction by K同学啊')
    plt.xlabel('Time')
    plt.ylabel('Stock Price')
    plt.legend()
    plt.show()
    

    在这里插入图片描述

    3.评估

    """
    MSE  :均方误差    ----->  预测值减真实值求平方后求均值
    RMSE :均方根误差  ----->  对均方误差开方
    MAE  :平均绝对误差----->  预测值减真实值求绝对值后求均值
    R2   :决定系数,可以简单理解为反映模型拟合优度的重要的统计量
    
    详细介绍可以参考文章:https://blog.csdn.net/qq_38251616/article/details/107997435
    """
    MSE   = metrics.mean_squared_error(predicted_stock_price, real_stock_price)
    RMSE  = metrics.mean_squared_error(predicted_stock_price, real_stock_price)**0.5
    MAE   = metrics.mean_absolute_error(predicted_stock_price, real_stock_price)
    R2    = metrics.r2_score(predicted_stock_price, real_stock_price)
    
    print('均方误差: %.5f' % MSE)
    print('均方根误差: %.5f' % RMSE)
    print('平均绝对误差: %.5f' % MAE)
    print('R2: %.5f' % R2)
    
    均方误差: 2688.75170
    均方根误差: 51.85317
    平均绝对误差: 44.97829
    R2: 0.74036
    

    拟合度除了更换模型外,还可以通过调整参数来提高,这里主要是介绍LSTM,就不对调参做详细介绍了。

    往期精彩内容:

    来自专栏:《深度学习100例》

    如果觉得本文对你有帮助记得 点个关注,给个赞,加个收藏


    最后再送大家一本,帮助大家拿到 BAT 等一线大厂 offer 的数据结构刷题笔记,是谷歌和阿里的大佬写的,对于算法薄弱或者需要提高的同学都十分受用(提取码:9go2 ):

    谷歌和阿里大佬的Leetcode刷题笔记

    以及我整理的7K+本开源电子书,总有一本可以帮到你 💖(提取码:4eg0)

    7K+本开源电子书

    展开全文
  • 从复杂系统的历史故障数据出发,提出了一种基于长短期记忆(LSTM)循环神经网络的故障时间序列预测方法,包括网络结构设计、网络训练和预测过程实现算法等,进一步以预测误差最小为目标,提出了一种基于多层网格搜索的LSTM...
  • 深度学习极大地推进了计算机视觉、自然语言处理和其他领域的最新技术。 该论文探讨了深度学习在汇率预测方面的潜力。... 尤其是在交易利润方面,更简单的神经网络的表现可能与更复杂的深度神经网络一样好,甚至更好。
  • 基于循环神经网络(RNN)预测分子性质 导入库 from rdkit import Chem from rdkit.Chem.Crippen import MolLogP import numpy as np import torch import time 载入数据,计算分子指纹和描述符 maxlen = 64 with ...
  • 时间序列是按时间顺序组织...长短期记忆网络(LSTM)是一种常用的循环神经网络,适合处理有更长时间跨度的内部记忆,被广泛应用于时间序列分析,能够保持数据的内在持续性,反映数据的细粒度走势,具有良好的预测效果。

    时间序列是按时间顺序组织的数字序列,是数据分析中重要的处理对象之一。时间序列的主要特点是数据获取方式一般具有客观性,能反映某种现象的变化趋势或统计指标,进而预测未来走向,这在本质上也是一个回归预测的问题。长短期记忆网络(LSTM)是一种常用的循环神经网络,适合处理有更长时间跨度的内部记忆,被广泛应用于时间序列分析,能够保持数据的内在持续性,反映数据的细粒度走势,具有良好的预测效果。

    一、数据集介绍

    厄尔尼诺-南方涛动(ENSO)是影响全球极端气候的重要因子,因此预估ENSO海温在全球变暖下的变化也是预估未来全球变暖下全球极端气候变化的重要因素之一。遗憾的是,最近20年来多次的全球耦合模式比较计划(CMIP)尽管对气候平均态和ENSO本身的模拟都取得了长足的进步,但是对未来增暖情形下ENSO海温异常强度的变化都存在显著的模式间差异。最近CMIP5预估的ENSO海温增强或减弱的模式个数基本相当,模式间的标准差远大于多模式集合平均的结果。因此揭示各模式预估ENSO海温振幅变化存在显著差异的核心物理过程是未来进一步改进模式、提高模式预估可信度的必要途径。
    MATLAB自带了enso的数据集,只需要load就可加载:

    load enso
    

    加载后,工作区增加了month和pressure两个168*1的数据。我们可以利用plot函数绘制enso的时间序列数据,绘制代码如下:

    load enso
    figure;plot(month,pressure,'k:',month,pressure,'r*');
    

    运行图像:
    在这里插入图片描述

    二、通过样条算法进行曲线拟合

    通过MATLAB提供的fit函数可以方便进行曲线拟合及预测分析,主要代码如下:

    close all;clear all;clc;
    rand('seed',10)  %设置随机数种子
    %加载数据
    load enso
    data_x=month;data_y=pressure;
    %样条拟合
    [res1,res2,res3]=fit(data_x,data_y,'smoothingspline');
    %绘图
    figure;
    subplot(2,1,1)
    plot(data_x,data_y,'r*');
    hold on;
    plot(res1,data_x,data_y);
    title(sprintf('样条分析-RMSE=%.2f',res2.rmse));
    subplot(2,1,2)
    stem(data_x,res3.residuals)
    xlabel('Time');ylabel('Error');
    title('样条分析-误差图');
    

    采用样条算法进行拟合并绘制误差曲线,其效果如下:
    在这里插入图片描述
    可以发现,直接采用样条算法可以得到平滑的拟合曲线,能在一定程度上反映数据的分布状况,但也存在较多的误差,其RMSE值为1.52,相对较大。

    三、基于MATLAB的LSTM预测

    3.1 定义LSTM网络函数

    函数代码如下:

    function layers=get_lstm_net(wd)
    %网络架构
    numFeatures=wd;
    numResponses=1;
    numHiddenUnits=250;
    
    layers=[sequenceInputLayer(numFeatures)
        lstmLayer(numHiddenUnits)
        dropoutLayer(0.1)
        lstmLayer(2*numHiddenUnits)
        dropoutLayer(0.1)
        fullyConnectedLayer(numResponses)
        regressionLayer];
    
    end
    

    定义完后,在命令行窗口可以调用该网络函数,并使用网络设计器进行可视化分析,核心代码如下:

     layers=get_lstm_net(5);
    deepNetworkDesigner
    

    效果如图所示:
    在这里插入图片描述
    可以发现,设计的网络共有7层,且最后一层为回归层。

    3.2 主函数

    主函数代码如下:

    close all;clear all;clc;
    rand('seed',10);  %设置随机数种子
    %% I.加载数据
    load enso
    data_x=month';
    data_y=pressure';
    %% II.数据预处理
    mu=mean(data_y);%计算均值
    sig=std(data_y);%计算标准差
    data_y=(data_y-mu)/sig;%数据归一化
    %% III.数据准备
    wd=5;
    len=numel(data_y);%计算data_y中元素数目
    wdata=[];
    for i=1:1:len-wd
        di=data_y(i:i+wd);
        wdata=[wdata;di];
    end
    wdata_origin=wdata;
    index_list=randperm(size(wdata,1));%整数随机排序
    ind=round(0.8*length(index_list));%四舍五入
    train_index=index_list(1:ind);
    test_index=index_list(ind+1:end);
    train_index=sort(train_index);
    test_index=sort(test_index);
    
    %% IV.划分训练集、测试集的数据和标签
    dataTrain=wdata(train_index,:);
    dataTest=wdata(test_index,:);
    XTrain=dataTrain(:,1:end-1)';
    YTrain=dataTrain(:,end)';
    XTest=dataTest(:,1:end-1)';
    YTest=dataTest(:,end)';
    
    %% V.网络构建
    layers=get_lstm_net(wd);
    options=trainingOptions('adam',...
        'MaxEpochs',1000,...
        'GradientThreshold',1,...
        'InitialLearnRate',0.005, ...
        'LearnRateSchedule','piecewise',...
        'LearnRateDropPeriod',125,...
        'LearnRateDropFactor',0.2,...
        'Verbose',0,...
        'Plots','training-progress');
    
    %% VI.训练
    net=trainNetwork(XTrain,YTrain,layers,options);
    %% VII.测试
    Xall=wdata_origin(:,1:end-1)';
    Yall=wdata_origin(:,end)';
    YPred=predict(net,Xall,'MiniBatchSize',1);
    rmse=mean((YPred(:)-Yall(:)).^2);
    
    %% VIII.显示
    figure,
    subplot(2,1,1)
    plot(data_x(1:length(Yall)),Yall)
    hold on;
    plot(data_x(1:length(Yall)),YPred,'.-')
    hold off;
    legend(['Real','Predict'])
    ylabel('Data')
    title(sprintf('LSTM分析-RMSE=%.2f',rmse));
    subplot(2,1,2)
    stem(data_x(1:length(Yall)),YPred-Yall)
    xlabel('Time');ylabel('Error');
    title('LSTM分析-误差图');
    

    训练过程如下。
    在这里插入图片描述

    采用LSTM模型进行拟合并绘制误差曲线,具体结果如下图所示。
    在这里插入图片描述

    由上图可以发现,采用LSTM模型可以得到较好的预测曲线,能在一定程度上反映数据的分布状况,误差相对较小,RMSE为0.46。

    ok,以上便是全部内容了,如果对你有所帮助,记得点个赞哟~

    参考:
    【1】https://ww2.mathworks.cn/help/curvefit/custom-nonlinear-enso-data-analysis.html

    展开全文
  • 文章目录一、前言二、RNN是什么三、准备工作1.设置GPU2.加载数据四、数据预处理1.归一化2.设置测试集训练集五、构建模型六、激活模型七、训练模型八、结果可视化1.绘制loss图2....深度学习100例-卷积神经网络
  • 循环神经网络> 数据集:(百度网盘) 链接:https://pan.baidu.com/s/1ozBoPhO7LU06z9mNlufbmg 提取码:59vk #基于。csv数据没建立rnn模型,预测 # 1.数据预处理,将序列数据转化为可用于rnn输入的数据 # 2.对新...
  • 神经网络LSTM 时间预测

    热门讨论 2017-08-03 09:50:05
    RNN全称循环神经网络(Recurrent Neural Networks),是用来处理序列数据的。在传统的神经网络模型中,从输入层到隐含层再到输出层,层与层之间是全连接的,每层之间的节点是无连接的。但是这种普通的神经网络对于很...
  • 循环神经网络(RNN)是一类非常强大的用于处理和预测序列数据的神经网络模型。循环结构的神经网络克服了传统机器学习方法对输入和输出数据的许多限制,使其成为深度学习领域中一类非常重要的模型。RNN及其变体网络已经...
  • 研究结果表明:相比于反向传播神经网络预测模型和双向循环神经网络预测模型,基于循环神经网络的煤矿工作面瓦斯浓度预测模型的训练误差降低至0.003,预测结果误差降低至0.006,具有更高的预测准确度;同时,预测误差...
  • 文章地址:https://blog.statsbot.co/time-series-anomaly-detection-algorithms-1cef5519aef2我们想用一个长短期记忆网络模型LSTM来讨论时间序列预测。这篇文章将告诉你如何利用时间序列分析来预测未来的货币汇率,...
  • 如何准备数据,开发和评估用于时间序列预测的LSTM递归神经网络。 1. 洗发水销售额数据集; 2. 测试设置; 3. 持续性模型预测; 4. LSTM数据准备; 5. LSTM模型开发; 6. LSTM预测; 7. 完整的LSTM例子; 8. 开发...
  • @(Aaron)[机器学习 | 循环神经网络] 主要内容包括: 基于循环神经网络的语言模型,提供了从零开始的实现与简洁实现 代码实践 文章目录循环神经网络的构造裁剪梯度代码实践 循环神经网络的构造   循环神经网络...
  • 文章讲解介绍:https://blog.csdn.net/qq_33302004/article/details/113951504
  • 关于循环神经网络预测的几点总结序列转监督如何预测 序列转监督 我们刚刚接触机器学习和深度学习时候,都是分类任务,那么分类任务和序列预测最大的区别就在于序列转监督的过程。其中牵扯3个量,一个是lookback...
  • MATLAB实现RNN(循环神经网络)时间序列预测数据集
  • (1)时序预测(2)绘制预测值和真实值对比曲线(3)绘制真实值和预测值的误差对比曲线(4)可以通过更改参数显示多个预测
  • 针对球轴承的剩余寿命预测问题,基于自组织映射(Self organizing map,SOM)和反向传播(Back propagation, BP)两种神经网络,提出一套新的预测球轴承剩余寿命的方法体系。深入对比分析几种不同轴承衰退指标的优缺点...
  • PyTorch--用循环神经网络LSTM预测时间序列

    千次阅读 多人点赞 2020-03-02 22:20:31
    使用PyTroch搭建LSTM预测时间序列 时间序列就是以时间为自变量的一系列数据。例如, 24小时的温度,各种产品一个月的价格变动, 一个公司一年的股票价格。 现在前沿深度学习模型比如LSTM能够捕捉时间序列的规律,因此...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 40,797
精华内容 16,318
关键字:

循环神经网络预测