循环神经网络-单变量序列预测详解(pytorch)

参考博客

文章目录

      • (1)导入所需要的包
      • (2)读取数据并展示
      • (3)数据预处理
      • (4)划分训练集和测试集
      • (5)构建RNN回归模型
      • (6)构造训练函数
      • (7)对整个数据集进行预测
      • (8)可视化展示
      • (9)MSE为评价指标

(1)导入所需要的包

import torch
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.preprocessing import MinMaxScaler

(2)读取数据并展示

data_csv =pd.read_csv("data/data.csv", usecols=[1])
plt.plot(data_csv)
print(data_csv.shape)

在这里插入图片描述

(3)数据预处理

缺失值,转化成numpy.ndarray类型,转化成float类型,归一化处理

data_csv = data_csv.dropna()
dataset = data_csv.values
dataset = dataset.astype("float32")
scaler = MinMaxScaler()
dataset = scaler.fit_transform(dataset)

(4)划分训练集和测试集

用30个预测一个
1-30:31
2-31:32

94-143:144
需要注意a = [dataset[i: (i + look_back)]],而不是a = dataset[i: (i + look_back)]

look_back = 30
def create_dataset(dataset, look_back):
    dataX, dataY = [], []
    for i in range(len(dataset) - look_back):
        a = [dataset[i: (i + look_back)]]
        dataX.append(a)
        dataY.append(dataset[i + look_back])
        
    return np.array(dataX), np.array(dataY)

dataX, dataY = create_dataset(dataset, look_back)
dataX.shape,dataY.shape,type(dataX),type(dataY),dataX.dtype,dataY.dtype

在这里插入图片描述对于 dataX,它的形状为 (114, 1, 30, 1)。其中 114 表示样本数量,1 表示特征数量,30 表示历史时间步的数量,1 表示每个时间步的特征数量。

输出部分dataX和dataY的值

print(dataX[:2],dataY[:2])

在这里插入图片描述

数据集搭好之后,对数据集进行7:3的划分

train_size=int(len(dataX)*0.7)
test_size=len(dataX)-train_size

train_x=dataX[:train_size]
train_y=dataY[:train_size]

test_x=dataX[train_size:]
test_y=dataY[train_size:]

print(train_size)

在这里插入图片描述

train_x=torch.from_numpy(train_x)
train_x=train_x.squeeze(3)
train_y=torch.from_numpy(train_y)

test_x=torch.from_numpy(test_x)
test_y=torch.from_numpy(test_y)
print(train_x.shape,test_x.shape)

在这里插入图片描述
对以上代码进行解释:

  • numpy.ndarray类型的转化成Tensor类型
  • 即将 NumPy 数组 train_x 转换为 PyTorch 张量
  • 转换之后神经网络才能计算
  • sequeeze(3)是将train_x从([79,1,30,1])变为([79,1,30])
  • test_x不需要sequeeze(3)的原因是:在pytorch中,卷积池化等操作需要输入的是四维张量(样本数,时间步长,特征数,1 )**(有待考究)**test在后面没用到

(5)构建RNN回归模型

class rnn_reg(torch.nn.Module):
    def __init__(self,input_size,hidden_size,out_size=1,num_layers=2)->None:
        super(rnn_reg,self).__init__()
        self.rnn=torch.nn.RNN(input_size,hidden_size,num_layers)
        self.reg=torch.nn.Linear(hidden_size,out_size)
    
    def forward(self,x):
        x,_=self.rnn(x)
        seq,batch_size,hidden_size=x.shape
        x=x.reshape(seq*batch_size,hidden_size)
        x=self.reg(x)
        x.reshape(seq,batch_size,-1)
        return x
    
net=rnn_reg(look_back,16)
criterion=torch.nn.MSELoss()
optimizer=torch.optim.Adam(net.parameters(),lr=1e-2)

对以上代码进行解释:

  • rnn_reg 的子类,继承torch.nn.Module,用于创建自定义的神经网络模型

  • __ init__是rnn_reg 类构造函数,用于初始化模型的参数
    在这里插入图片描述

  • super(rnn_reg, self).__init__(): 调用父类 torch.nn.Module 的构造函数

  • self.rnn = torch.nn.RNN(input_size, hidden_size, num_layers): 创建了一个 RNN 层。input_size 表示输入特征的维度,hidden_size 表示隐藏状态的维度,num_layers 表示 RNN 的层数。

  • self.reg = torch.nn.Linear(hidden_size, out_size): 创建了一个线性层(全连接层),用于将 RNN 的隐藏状态映射到输出特征维度。

  • def forward(self, x): 这是 rnn_reg 类的前向传播方法。它接受输入 x,并定义了模型的前向计算过程。
    -在这里插入图片描述

  • x, _ = self.rnn(x): 将输入 x 传递给 RNN 层进行前向计算。_ 表示隐藏状态,由于这里不需要使用隐藏状态,所以用下划线 _ 进行占位。

  • seq, batch_size, hidden_size = x.shape: 获取 RNN 输出 x 的形状信息,其中 seq 表示序列长度,batch_size 表示批次大小,hidden_size 表示隐藏状态的维度。

  • x = x.reshape(seq * batch_size, hidden_size): 将 x 重塑为形状 (seq * batch_size, hidden_size),以便通过线性层进行映射。

  • x = self.reg(x): 将重塑后的 x 传递给线性层 self.reg 进行映射操作。

  • x.reshape(seq, batch_size, -1): 将输出 x 重塑为形状 (seq, batch_size, -1),以便与输入保持相同的维度。

  • return x: 返回最终的输出 x。

  • net = rnn_reg(look_back, 16): 创建了一个 rnn_reg 类的实例 net。look_back 表示输入特征的维度,16 表示隐藏状态的维度。

  • criterion = torch.nn.MSELoss(): 定义了损失函数,使用均方误差(MSE)作为损失函数。

  • optimizer = torch.optim.Adam(net.parameters(), lr=1e-2): 定义了优化器,使用 Adam 优化算法来更新模型的参数,学习率为 1e-2。

输出一下设置的模型内的一些层数的维度:

for param_tensor in net.state_dict():
    print(param_tensor,'\t',net.state_dict()[param_tensor].size())

在这里插入图片描述

(6)构造训练函数

设置训练1000次,每100次输出一次损失

running_loss=0.0
for epoch in range(1000):
    var_x=train_x
    var_y=train_y
    out=net(var_x)
    loss=criterion(out,var_y)
    running_loss+=loss.item()
    optimizer.zero_grad()
    loss.backward()
    optimizer.step()
    if(epoch+1)%100==0:
        print('Epoch:{},loss:{:.5f}'.format(epoch+1,running_loss/100))
        running_loss=0.0
        

在这里插入图片描述
对以上代码进行解释:

  • running_loss,用于记录每个训练周期的累计损失。
  • out=net(var_x)这个out就是红框标出的需要预测的预测值,即将输入数据 var_x 通过神经网络模型 net 进行前向传播,得到输出 out。
    在这里插入图片描述
  • loss = criterion(out, var_y): 计算模型输出 out 和目标标签 var_y 之间的损失,使用预先定义的损失函数 criterion(在代码中是均方误差)。
  • loss.item() 方法用于获取 loss 的数值(标量),然后将其加到 running_loss 上。
  • optimizer.zero_grad(): 清空优化器中之前的梯度信息,以便进行下一次的反向传播。
  • loss.backward(): 执行反向传播,计算损失函数关于模型参数的梯度。
  • optimizer.step(): 这行代码根据计算得到的梯度更新模型参数,使用优化器中定义的Adam优化算法
  • print输出平均损失

(7)对整个数据集进行预测

net = net.eval() # 转换成测试模式
data_x = dataX.reshape(-1, 1, look_back)
data_x = torch.from_numpy(data_x).to(torch.float32)
var_data = data_x
pred_test = net(var_data) # 测试集的预测结果
pred_test = pred_test.view(-1).data.numpy()

对上述代码解释:
在这里插入图片描述
在这里插入图片描述

  • data_x = torch.from_numpy(data_x).to(torch.float32): 这行代码将 NumPy 数组 data_x 转换为 PyTorch 的 Tensor 对象,并将数据类型设置为 torch.float32。这是为了与神经网络模型的数据类型匹配。
  • pred_test = pred_test.view(-1).data.numpy(): 这行代码对预测结果进行处理,首先使用 view(-1) 将输出结果展平为一维张量,然后使用 data.numpy() 将结果转换为 NumPy 数组,以便后续的分析和可视化。

(8)可视化展示

这里因为用30个预测1个,所以dataset进行了切片(总共114)

plt.plot(pred_test, 'deeppink', label='prediction')
plt.plot(dataset[look_back:], 'green', label='real')
plt.legend(loc='best')

在这里插入图片描述

(9)MSE为评价指标

这里因为用30个预测1个,所以计算MSE的也不包括前30个数据,否则没法去计算

from sklearn.metrics import mean_squared_error
MSE = mean_squared_error(dataset[look_back:], pred_test)
print(MSE)

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/327947.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

Vue3响应式系统(三)

Vue3响应式系统(二)https://blog.csdn.net/qq_55806761/article/details/135612738 七、无限递归循环。 响应式系统里无限递归也是需要考虑到的。 什么情况会出现无限递归循环? 代码示例: const data { foo: 1 } const obj new Proxy(/* * */) effe…

金融CRM系统是什么?有哪些功能和作用

今年市场经济下行,投资趋向于保守、人们消费降级,对于金融行业来说影响很大。受经济形式的影响加上行业的数字化转型升级,金融企业都在寻求客户管理的新策略,维护好忠实客户、吸引新客户投资。小编认为CRM系统是管理客户的不二之选…

LLM之RAG实战(十六)| 使用Llama-2、PgVector和LlamaIndex构建LLM Rag Pipeline

近年来,大型语言模型(LLM)取得了显著的进步,然而大模型缺点之一是幻觉问题,即“一本正经的胡说八道”。其中RAG(Retrieval Augmented Generation,检索增强生成)是解决幻觉比较有效的…

ROS第 6 课 编写简单的订阅器 Subscriber

文章目录 第 6 课 编写简单的订阅器 Subscriber1. 编写订阅者节点2. 测试发布者和订阅者 第 6 课 编写简单的订阅器 Subscriber 订阅器是基于编辑了发布器的基础上创建的,只有发布了消息,才有可能订阅。若未编辑发布器,可前往"ROS第5课 …

C语言练习day7

数包含9的数 包含数字9的数_牛客题霸_牛客网 题目: 思路:首先,我们得生成1~2019之间的数字,其次再通过各个位数来比较是否等于9,若等于,则记录一次,反之,不记录。 代码演示&…

MATLAB - 加载预定义的机器人模型

系列文章目录 前言 一、 要快速访问常见的机器人模型,可使用 loadrobot 功能,该功能可加载市售的机器人模型,如 Universal Robots™ UR10 cobot、Boston Dynamics™ Atlas 人形机器人和 KINOVA™ Gen 3 机械手。探索如何生成关节配置并与机器…

SAP银企直联报错排查方法与步骤-F110

银企直联的报错排查经常需要利用F110来查询。方法步骤如下: 1、首先要确定报错是哪天的,并且当天那一次跑的付款建议。需要通过表 REGUH来确认(跟据供应商编码、日期) 2、通过REGUH表的信息知道了是2024年1月16号第5个标识(也就是第五次跑付…

【QML COOK】- 010-动态创建组件

上节介绍了Component的概念,本节介绍一下如何使用javascript动态创建对象。 1. 创建工程,新建一个MyComponent.qml的qml import QtQuickRectangle {color: "red" }它很简单就是一个红色框 2. 编辑main.qml import QtQuickWindow {id: root…

刘知远LLM入门到实战——自然语言基础

文章目录 自然语言处理基础词表示语言模型N-gram ModelNeural Language Model: 为什么NLP等领域的模型越来越大? 大模型会带来哪些新的范式和挑战? 自然语言处理基础 让计算机理解人类语言,图灵测试就是基于对话的方式。 研究历史&#xff…

SpringBoot:详解依赖注入和使用配置文件

🏡浩泽学编程:个人主页 🔥 推荐专栏:《深入浅出SpringBoot》《java项目分享》 《RabbitMQ》《Spring》《SpringMVC》 🛸学无止境,不骄不躁,知行合一 文章目录 前言一、&#x1f3…

django后台手机号加密存储

需求: 1 :员工在填写用户的手机号时,直接填写,在django后台中输入 2:当员工在后台确认要存储到数据库时,后台将会把手机号进行加密存储,当数据库被黑之后,手机号字段为加密字符 3&am…

青少年的敏感心理

这几天的某个闲暇时刻,突然想起一个有意思的话题。关于青少年的心理,尤其是青春期的心理,这是敏感的一种心理状态。 依稀记得那大概是初一或者是更低年级的样子,当时父母外出务工,高中以前都是和奶奶一起长大。具体事…

数据科学与大数据导论期末复习笔记(大数据)

来自于深圳技术大学,此笔记涵盖了期末老师画的重点知识,分享给大家。 等深分箱和等宽分箱的区别:等宽分箱基于数据的范围来划分箱子,每个箱子的宽度相等。等深分箱基于数据的观测值数量来划分箱子,每个箱子包含相同数量…

跟着cherno手搓游戏引擎【8】按键和鼠标的KeyCode

自定义KeyCode 先把glfw3.h里的KeyCode的定义抄到咱这里来。 在YOTO下创建KeyCode.h: #pragma once#ifdef YT_PLATFORM_WINDOWS///从glfw3中拿的 #define YT_KEY_SPACE 32 #define YT_KEY_APOSTROPHE 39 /* */ #define YT_KEY_COMMA 44…

Video 不支持微信小程序的show-bottom-progress属性

原文地址:Video 不支持微信小程序的show-bottom-progress属性-鹭娃网络 相关平台 微信小程序 小程序基础库: 2.20.1使用框架: React 复现步骤 import { Video} from tarojs/components; 渲染一个Video播放视频,无法隐藏手机屏幕最底部的进度条&#…

springcloud Alibaba中gateway和sentinel联合使用

看到这个文章相信你有一定的sentinel和gateway基础了吧。 官网的gateway和sentinel联合使用有些过时了,于是有了这个哈哈,给你看看官网的: 才sentinel1.6,现在都几了啊,所以有些过时。 下面开始讲解: 首先…

day02_计算机常识丶第一个程序丶注释丶关键字丶标识符

计算机常识 计算机如何存储数据 计算机世界中只有二进制。那么在计算机中存储和运算的所有数据都要转为二进制。包括数字、字符、图片、声音、视频等。 进制 进制也就是进位计数制,是人为定义的带进位的计数方法 实例: // 在java 中 可以使用不同…

Linux实操学习

Linux常用操作 一、帮助命令1. man1.1 基本语法1.2 快捷键1.3 注意事项 2. help2.1 基本语法2.2 注意事项 3. 常用快捷键 二、文件目录类1. 常规操作1.1 pwd1.2 cd1.3 ls 2. 文件夹操作2.1 mkdir2.2 rmdir 3. 文件操作3.1 touch3.2 cp3.3 rm3.4 mv 4. 文件查看4.1 cat4.2 more4…

【视觉SLAM十四讲学习笔记】第五讲——相机模型

专栏系列文章如下: 【视觉SLAM十四讲学习笔记】第一讲——SLAM介绍 【视觉SLAM十四讲学习笔记】第二讲——初识SLAM 【视觉SLAM十四讲学习笔记】第三讲——旋转矩阵 【视觉SLAM十四讲学习笔记】第三讲——旋转向量和欧拉角 【视觉SLAM十四讲学习笔记】第三讲——四元…

部署本地GPT

在现实生活中,很多公司或个人的资料是不愿意公布在互联网上的,但是我们又要使用人工智能的能力帮我们处理文件、做决策、执行命令那怎么办呢?于是我们构建自己或公司的本地专属GPT变得非常重要。 先看效果: 查资料不用愁 家教不…