当前位置: 首页 > article >正文

RNN(循环神经网络)详解

1️⃣ RNN介绍

前馈神经网络(CNN,全连接网络)的流程是前向传播、反向传播和参数更新,存在以下不足:

  • 无法处理时序数据:时序数据长度一般不固定,而前馈神经网络要求输入和输出的维度是固定的,不能改变
  • 缺少记忆:前馈神经网络没有机制去记忆和处理之前的输入数据,因此无法处理像语言、股票走势或天气预报等 序列化时间依赖性强的数据

针对前馈神经网络上述问题,RNN引入以下机制:

  • 不同时间步的隐藏层之间是相连的
  • 在时刻t,隐藏层的输入包括两部分,当前时刻的输入 x t x_t xt和上一个时间步隐藏层的输出 s t − 1 s_{t-1} st1

通过这两条机制,模型能够记忆之前的输入数据,捕捉序列的上下文信息

看完这几句话你一定在想,这说的是个啥?太晕了,没关系,慢慢往下看

多说一句,RNN在很久之前就提出了,Jordan RNN于1986被提出,Elman RNN于1990年提出。


2️⃣ 原理介绍

接下来,讲讲具体原理,解决一下上面的迷惑。看下面这张图,分析一下 o t o_t ot的表达式:
在这里插入图片描述

  • x t x_t xt是t时刻的输入
  • s t s_t st是t时刻的记忆, s t = f ( U ⋅ x t + W ⋅ s t − 1 ) s_t=f(U\cdot x_t+W\cdot s_{t-1}) st=f(Uxt+Wst1),f表示激活函数, s t − 1 s_{t-1} st1表示t-1时刻的记忆
  • o t o_t ot是t时刻的输出, o t = s o f t m a x ( V ⋅ s t ) o_t=softmax(V\cdot s_t) ot=softmax(Vst)

看完上面这张图,对于W是什么疑惑很大,我一开始学习的时候也是这样,W到底是啥呢?来看下面这张图:
在这里插入图片描述

看完这张图,对于W的描述一目了然。W是在不同的时间步 隐藏层之间递归的权重。在RNN中,不同时间步使用相同的W,为了保证信息能够传递下去。

其实这里还有一个疑惑,按照我之前的认知,神经网络可训练的参数w和b都是在神经元上的,例如下面这张图。那么问题来了,RNN隐藏层神经元上参数是啥样的呢?
在这里插入图片描述
虽然下面的左图是这样画的,搞得好像参数U,W,V“漂浮在空中一般”,实际上,它们都在神经元上。准确的来说应该是右图的形式,U和W都在隐藏层神经元上,V在输出层神经元上。所以之前理解的神经元是一个神经元上只有一种参数。对于RNN来说,隐藏层神经元上有两种参数U和W。终于搞懂了,爽!
在这里插入图片描述
分析完RNN中参数的具体含义,来看看参数的尺寸:
U = 隐藏层神经元个数 × 输入尺寸 W = 隐藏层神经元个数 × 隐藏层神经元个数 V = 输出尺寸 × 隐藏层神经元个数 U=隐藏层神经元个数×输入尺寸\\ W=隐藏层神经元个数×隐藏层神经元个数\\ V=输出尺寸×隐藏层神经元个数 U=隐藏层神经元个数×输入尺寸W=隐藏层神经元个数×隐藏层神经元个数V=输出尺寸×隐藏层神经元个数
这样最简单的RNN就分析完了。


3️⃣ 代码

接下来看一下最简单的代码:

import torch
import torch.nn as nn

# 参数设置
input_size = 2    # 每个时间步的特征维度
hidden_size = 5   # 隐层神经元数量
num_layers = 1    # RNN层数
output_size = 3   # 假设输出的维度

# RNN对象实例化
rnn = nn.RNN(input_size, hidden_size, num_layers, batch_first=True)

# U:输入到隐藏状态的权重矩阵
U = rnn.weight_ih_l0  # 输入到隐藏状态的权重矩阵
print("矩阵 U 的大小 (输入到隐藏层):", U.shape)  # 应为 (hidden_size, input_size)

# W:隐藏状态到隐藏状态的权重矩阵
W = rnn.weight_hh_l0  # 隐藏状态之间的递归权重矩阵
print("矩阵 W 的大小 (隐藏层到隐藏层):", W.shape)  # 应为 (hidden_size, hidden_size)

# V:输出层权重矩阵
# 在 PyTorch 中没有直接实现,可以添加一个 Linear 层来模拟
V_layer = nn.Linear(hidden_size, output_size)  # 定义线性层
V = V_layer.weight  # V 就是隐藏状态到输出层的权重矩阵
print("矩阵 V 的大小 (隐藏层到输出层):", V.shape)  # 应为 (output_size, hidden_size)

输出:

矩阵 U 的大小 (输入到隐藏层): torch.Size([5, 2])
矩阵 W 的大小 (隐藏层到隐藏层): torch.Size([5, 5])
矩阵 V 的大小 (隐藏层到输出层): torch.Size([3, 5])

4️⃣ 总结

  • 标准的RNN存在梯度消失梯度爆炸问题,无法捕捉长时间序列的关系。因此LSTM和GRU被提出

5️⃣ 参考

  • 深度学习-神经网络-循环神经网络(一):RNN(Recurrent Neural Network,循环神经网络;1990年)
  • 理解循环神经网络(RNN)

http://www.kler.cn/a/390899.html

相关文章:

  • Jmeter基础篇(22)服务器性能监测工具Nmon的使用
  • 冗余连接2 hard题 代随C#写法
  • SAP_MM_SD_PP_FICO_视频课程几乎免费送
  • ReactPress技术揭秘
  • 5G时代的关键元件:射频微波MLCCs市场前景广阔
  • 【Spring】@Autowired与@Resource的区别
  • 【独立同分布】
  • LeetCode 二分算法 范围内整数的最大得分
  • [CUDA] cuda kernel开发记录
  • HTTP TCP三次握手深入解析
  • ESLint 使用教程(七):ESLint还能校验JSON文件内容?
  • XSS漏洞--常用payload及绕过
  • 关于解决使用VMWare内的虚拟机无法识别USB问题小结
  • 【JavaEE】文件io
  • Yocto项目 - 小心Overrides机制还用在Tasks中
  • mysql占用内存过大问题排查
  • java 递归算法案例讲解
  • Linux——简单认识vim、gcc以及make/Makefile
  • Python数据分析NumPy和pandas(二十六、数据整理--连接、合并和重塑 之三:重塑和透视)
  • uniapp路由与页面跳转详解:API调用与Navigator组件实战
  • 如何使用腾讯云GPU云服务器自建一个简单的类似ChatGPT、Kimi的会话机器人
  • OpenCV与AI深度学习 | 基于YoloV11自定义数据集实现车辆事故检测(有源码,建议收藏!)
  • vue中如何关闭eslint检测?
  • 【子串分值——贡献法】
  • 软考:去中心化的部署有什么特点
  • vue2面试题6|[2024-11-11]