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

【NLP】daydayup 循环神经网络基本结构,pytorch实现

RNN 循环神经网络

循环神经网络(Recurrent Neural Network,RNN)是一种神经网络结构,专门用于处理序列数据。

RNN结构原理

在这里插入图片描述

RNN架构中,网络通过循环把信息从一个处理步骤传递到下一个,这个循环结构被称为隐藏层状态或者隐藏状态。可以捕捉并储存已经出处理的序列元素信息。

这个过程可以简化为
s t = f ( U ⋅ x t + W ⋅ s t − 1 ) s_t=f(\mathbf{U}·x_t+\mathbf{W}·s_{t-1}) st=f(Uxt+Wst1)
U是输入到隐藏的权重矩阵

W是隐藏到隐藏的权重

在这里插入图片描述

输出层 O t {O}_{t} Ot = g(V s t {s}_{t} st)

V是隐藏层到输出层的矩阵

在这里插入图片描述

import numpy as np
import torch
import torch.nn as nn# 假设输入3个时间步
x = np.random.rand(3,2) 
# 一个样本的输入,如文本中的一句话,一个样本中的3个特征,一句话有3个词,每个特征的维度是2,词向量的维度是2# 定义rnn参数
input_size = 2
hidden_size = 3
output_size = 4# 初始化权重和偏置
W_xh = np.random.rand(input_size,hidden_size) # 输入到隐藏
W_hh = np.random.rand(hidden_size,hidden_size) # 隐藏到隐藏
W_hy = np.random.rand(hidden_size,output_size) # 隐藏到输出bh = np.zeros(hidden_size) # 隐藏层偏置
by = np.zeros(output_size) # 输出层偏置# 激活函数
def tanh(x):return np.tanh(x)# 初始化隐藏状态
H_prev = np.zeros(hidden_size)x1 = x[0] # 得到第一个输入特征 文本序列中的第一个词
H1 = tanh(np.dot(x1,W_xh)+H_prev+bh)
print('隐藏1:',H1)
O1 = np.dot(H1,W_hy)+by
print('输出1:',O1)x2 = x[1]
H2 = tanh(np.dot(x2,W_xh)+np.dot(H1,W_hh)+bh)
print('隐藏2:',H2)
O2 = np.dot(H2,W_hy)+by
print('输出2:',O2)x3 = x[1]
H3 = tanh(np.dot(x3,W_xh)+np.dot(H2,W_hh)+bh)
print('隐藏3:',H3)
O3 = np.dot(H3,W_hy)+by
print('输出3:',O2)

RNNcell

PyTorch循环神经网络

import torch
import torch.nn as nnx = torch.randn(10,6,5) # 10批次大小 6词数 5向量维度
# 一次输入10句话,一句话中有6个词(特征),词向量维度是5(特征维度)class RNN(nn.Module):def __init__(self,input_size,hidden_size,batch_first=True):# input_size 输入的词向量维度,特征维度# hidden_size 隐藏状态的张量维度# batch_first 第一维度是否是batch,如果是,需要维度转换,以符合RNNcell的输入super().__init__()self.rnn_cell = nn.RNNCell(input_size,hidden_size)self.hidden_size = hidden_sizeself.batch_first = batch_firstdef __initialize_hidden(self,batch_size):# 初始化隐藏状态  第一个时间步没有隐藏的输入,需要初始化return torch.zeros((batch_size,self.hidden_size))def forward(self,x,init_hidden=None):# 得到数据的各个维度if self.batch_first:  # 维度转换 以符合cell输入bach_size,seq_size,input_size = x.size()x = x.permute(1,0,2)else:seq_size,bach_size,input_size = x.size()hiddens = [] # 储存隐藏状态if init_hidden is None: # 如果是第一个输入init_hidden = self.__initialize_hidden(bach_size)init_hidden = init_hidden.to(x.device) # 同步设备hidden_t = init_hiddenfor t in range(seq_size):hidden_t = self.rnn_cell(x[t],hidden_t)hiddens.append(hidden_t)hiddens = torch.stack(hiddens) # 堆叠所有时间步隐藏输出,合并为一个张量if self.batch_first:hiddens = hiddens.permute(1,0,2)print(hiddens)return hiddensmodel = RNN(5,8) # imput_size 词向量的维度 hidden_size 输出的维度  隐藏状态的张量维度
outputs = model(x)
print(outputs.shape) # torch.Size([10, 6, 8])

**这里并没有进行out的输出,只是获得了隐藏状态,在实际的需求中,需要增加其他的结构如线性层对隐藏状态进行操作 **

RNN

基于pytorch实现

import torch
import torch.nn as nn# 超参数设置batch_size,seq_size,input_size = 10,6,5 # 批次 句子长度 词向量维度hidden_size = 3  # 隐藏状态的张量维度# 数据
x = torch.rand(batch_size,seq_size,input_size)# 初始化隐藏状态
h_prev = torch.zeros(batch_size,hidden_size)# 创建RNNrnn = nn.RNN(input_size, hidden_size,batch_first=True) # batch_first=True是否转化out, hide= rnn(x,h_prev.unsqueeze(0))  # 返回值 第一个值为输出  第二个值是状态信息print(out.shape) # torch.Size([10, 6, 3])
print(hide.shape) # torch.Size([1, 10, 3])

biRNN双向RNN

双向RNN,使得模型能够学习到序列中某一点前后的上下文信息

在这里插入图片描述

import torch
import torch.nn as nn# 超参数设置batch_size,seq_size,input_size = 10,6,5 # 批次 句子长度 词向量维度hidden_size = 3  # 隐藏状态的张量维度# 数据
x = torch.rand(batch_size,seq_size,input_size)# 初始化隐藏状态
h_prev = torch.zeros(batch_size,hidden_size)# 创建RNNrnn = nn.RNN(input_size, hidden_size,batch_first=True,bidirectional=True) # batch_first=True是否转化out, hide= rnn(x)  # 返回值 第一个值为输出  第二个值是状态信息print(out.shape) # torch.Size([10, 6, 6])  这里直接合并了双向的隐藏状态
print(hide.shape) # torch.Size([2, 10, 3]) 输出的是正向和反向的隐藏状态

相关文章:

  • JavaScript 可视化案例详解
  • 如何在本地和远程删除 Git 分支
  • 微信小程序map组件自定义气泡真机不显示
  • 【Python语言初识(六)】
  • ubuntu22.04取消开机输入密码(实测)
  • 深入理解华为仓颉语言的数值类型
  • 在idea使用nacos微服务
  • Qt day1登录界面设计
  • 提取出来的ip与我原本的ip是在同一个区吗
  • 在线表格技术如何助力企业实现全面预算?
  • k8s基于nfs创建storageClass
  • React 组件命名规范
  • 【TypeScript学习】TypeScript基础学习总结二
  • 基于STM32的智能照明控制系统设计:MQTT通信与Web界面开发
  • 虾皮Java后台开发校园招聘面试题及参考答案
  • 【从零开始安装kubernetes-1.7.3】2.flannel、docker以及Harbor的配置以及作用
  • docker容器内的网络抓包
  • dva中组件的懒加载
  • JDK 6和JDK 7中的substring()方法
  • js递归,无限分级树形折叠菜单
  • Linux链接文件
  • Netty 4.1 源代码学习:线程模型
  • react-native 安卓真机环境搭建
  • Vue.js源码(2):初探List Rendering
  • 反思总结然后整装待发
  • 技术:超级实用的电脑小技巧
  • 为什么要用IPython/Jupyter?
  • NLPIR智能语义技术让大数据挖掘更简单
  • 扩展资源服务器解决oauth2 性能瓶颈
  • #HarmonyOS:Web组件的使用
  • #Js篇:单线程模式同步任务异步任务任务队列事件循环setTimeout() setInterval()
  • (3)llvm ir转换过程
  • (Matalb回归预测)PSO-BP粒子群算法优化BP神经网络的多维回归预测
  • (带教程)商业版SEO关键词按天计费系统:关键词排名优化、代理服务、手机自适应及搭建教程
  • (附源码)spring boot建达集团公司平台 毕业设计 141538
  • (附源码)计算机毕业设计大学生兼职系统
  • (四)Linux Shell编程——输入输出重定向
  • (一)基于IDEA的JAVA基础10
  • (原創) 人會胖會瘦,都是自我要求的結果 (日記)
  • .“空心村”成因分析及解决对策122344
  • .chm格式文件如何阅读
  • .Net core 6.0 升8.0
  • .NET/C# 将一个命令行参数字符串转换为命令行参数数组 args
  • .NET/C# 如何获取当前进程的 CPU 和内存占用?如何获取全局 CPU 和内存占用?
  • .NET/C# 使用反射调用含 ref 或 out 参数的方法
  • .NET处理HTTP请求
  • .net经典笔试题
  • .NET框架
  • .NET中 MVC 工厂模式浅析
  • .skip() 和 .only() 的使用
  • .vimrc 配置项
  • [20171101]rman to destination.txt
  • [240607] Jina AI 发布多模态嵌入模型 | PHP 曝新漏洞 | TypeScript 5.5 RC 发布公告
  • [AAuto]给百宝箱增加娱乐功能
  • [Android]竖直滑动选择器WheelView的实现