如果不加特别说明RNN的计算一般是从左到右的即第t步的特征计算只能“看到”的信息但从语义理解的角度来看有时只看前边时间步的信息是不够的。我们来看下边的例子。南京市 长江 大桥 是 一个 工程 奇迹。 南京 市长 江大桥 是 一个 好同志。“南京市长江大桥”这个短语的理解存在歧义在没有看到后边的上下文时无法对其进行正确的分词。双向RNN使得模型可以同时看到前边和后边的信息。上图显示的是利用双向RNN的示意图。在计算时先从前到后计算再将作为后向RNN序列的初始化 (相当于)再从后到前依次计算。前向RNN和后向RNN是两套独立的RNN它们的参数是不同的。在前向RNN的计算中包含了全部的序列信息在后向RNN的计算中包含了全部的序列信息。在进行序列分类任务时我们将与合并在一起作为整个序列的表征。在经过输出层之后 (Linear Softmax)最后输出其中Y为表示预测输出的随机变量概率的预测公式为在进行序列标注任务时将与合并在一起其中集成了的信息集成了的信息因此能够看到序列里全部的信息。之后基于计算每个时间步的输出其中test_rnn_sequence_labeling.py# -*- coding: utf-8 -*- 基于 RNN 的序列标注Sequence Labeling示例程序 功能使用单层 RNN 对句子中的每个字符进行标注S/B/M/E 四类并演示一次完整的训练迭代前向传播 → 计算损失 → 反向传播 → 参数更新。 标注体系 S (Single) : 单字词 B (Begin) : 词首 M (Middle) : 词中 E (End) : 词尾 运行前提 1. 当前目录下存在 vocab.txt词表文件 2. 同目录下存在 tokenizer.py提供 MyTokenizer 类。 import torch.nn as nn import torch from tokenizer import MyTokenizer import torch.optim as optim class MySequenceLabelingModel(nn.Module): 基于 RNN 的序列标注模型。 结构Embedding词嵌入 → RNN循环层 → Linear输出层 输入形如 (batch_size, max_length) 的词索引矩阵 输出形如 (batch_size, max_length, output_dim) 的 logits 矩阵 def __init__(self, vocab_size, embedding_dim, hidden_dim, output_dim, pad_id0, embedding_matrixNone): 初始化模型各层。 Args: vocab_size: 词表大小即 Embedding 的词典数量。 embedding_dim: 词向量维度。 hidden_dim: RNN 隐藏层维度。 output_dim: 输出类别数此处为标签类别数 4。 pad_id: padding 位置对应的词表索引其向量恒为 0 且不参与更新。 embedding_matrix: 预训练词向量矩阵torch.Tensor为 None 时随机初始化 Embedding。 super().__init__() # 词嵌入层支持随机初始化与预训练初始化两种方式 if embedding_matrix is None: # 随机初始化词向量 self.embedding nn.Embedding(vocab_size, embedding_dim, padding_idxpad_id) else: # 使用预训练矩阵初始化freezeFalse 表示随训练微调 self.embedding nn.Embedding.from_pretrained(embeddingsembedding_matrix, freezeFalse, padding_idxpad_id) # 循环层单层标准 RNN默认 tanh 激活batch_firstTrue 使输入为 (batch, seq, feat) self.rnn nn.RNN(input_sizeembedding_dim, hidden_sizehidden_dim, batch_firstTrue) # 输出层将每个时间步的隐藏状态映射为各类别的 logits self.linear nn.Linear(hidden_dim, output_dim) def forward(self, inputs): 前向传播。 Args: inputs: 词索引张量tensor形状 (batch_size, max_length)。 Returns: 每个位置各类别的 logits形状 (batch_size, max_length, output_dim)。 # 词嵌入索引 → 词向量 (batch_size, max_length, embedding_dim) embedding_outputs self.embedding(inputs) # RNN 编码返回所有时间步输出与最后一步隐藏状态此处只需前者 (batch_size, seq_len, hidden_dim) rnn_outputs, _ self.rnn(embedding_outputs) # 线性输出层每个时间步独立映射 (batch_size, seq_len, output_dim) return self.linear(rnn_outputs) if __name__ __main__: # ---------- 1. 数据准备 ---------- # 加载词表相对路径需在项目根目录运行 tokenizer MyTokenizer(vocab.txt) # 标签编码S单字词、B词首、M词中、E词尾 label_dict { S: 0, B: 1, M: 2, E: 3 } # 训练样本两个短句及其逐字标签标签长度与句长一一对应 texts [今天天气很好。, 但是明天要下雨。] labels [BEBEBES, BEBESBES] # 统一序列长度最长句子字符数 4s、/s 各占 1 位再预留 2 位 max_length max([len(text) for text in texts]) 4 samples [] # 存放 (x, y) 样本对 for text, label in zip(texts, labels): # 句子首尾添加开始/结束标记 char_list [s] [char for char in text] [/s] # 标签序列首尾对应补 S label_list [S] [label for label in label] [S] # 字符 → 词表索引 x [tokenizer.word2index[c] for c in char_list] # 标签字符 → 数字标签 y [label_dict[l] for l in label_list] # 不足 max_length 的部分补齐 if len(x) max_length: x [tokenizer.pad_id] * (max_length - len(x)) # 输入用 pad_id 填充 y [-100] * (max_length - len(y)) # padding 位置的 label 设置为 -100 (标签用 -100 填充)会被 CrossEntropyLoss 忽略 samples.append((x, y)) # ---------- 2. 构建模型、损失函数与优化器 ---------- model MySequenceLabelingModel(len(tokenizer.vocab), 300, 300, 4, None) loss_fn nn.CrossEntropyLoss() optimizer optim.SGD(model.parameters(), lr0.01) # ---------- 3. 前向传播与损失计算 ---------- batch_x torch.LongTensor([sample[0] for sample in samples]) batch_y torch.LongTensor([sample[1] for sample in samples]) print(batch_x.shape, batch_y.shape) outputs model(batch_x) preds outputs.reshape(-1, 4) labels batch_y.reshape(-1) loss loss_fn(preds, labels) print(loss) # ---------- 4. 反向传播与参数更新 ---------- loss.backward() optimizer.step() optimizer.zero_grad() # ---------- 5. 验证更新后再前向一次loss 应有所下降 ---------- outputs model(batch_x) preds outputs.reshape(-1, 4) loss loss_fn(preds, labels) print(loss)tokenizer.pyimport fasttext import torch import numpy as np class MyTokenizer: def __init__(self, vocab, padpad): self.vocab self.load_vocab(vocab) self.vocab_size len(self.vocab) self.word2index {word: i for i, word in enumerate(self.vocab)} self.index2word {i: word for i, word in enumerate(self.vocab)} self.pad pad self.pad_id self.word2index[pad] def tokenize(self, text): words text.split() return [self.word2index[word] for word in words if word in self.vocab] staticmethod def load_vocab(file_path): vocab [] with open(file_path, r) as f: for line in f.readlines(): vocab.append(line.strip()) return vocab #def tokenize_file(toknizer, input_file, output_file): # with open(input_file, r) as f: # with open(output_file, w) as out: # for line in f.readlines(): # try: # label, text line.strip().split(\t) # tokenized_text tokenizer.tokenize(text) # out.write(label \t .join(map(str, tokenized_text)) \n) # except: # continue ## main #if __name__ __main__: # # tokenizer MyTokenizer(vocab.txt, cc.zh.300.bin) # #vectors tokenizer.get_vector_tensor() # # tokenize_file(tokenizer, data/toutiao_cat_data_train_2.txt, data/toutiao_cat_data_train_2_tokenized.txt) # #tokenize_file(tokenizer, toutiao_cat_data_test.txt, toutiao_cat_data_test_tokenized.txt)
企业数字化 ERP 产品动态
相关推荐
【股票交易】专栏介绍 为什么同一家公司的经营状况没有明显变化,股价却可能上涨或下跌 30%?
因为股价不仅反映公司当下的经营结果,还包含市场对未来增长、资金成本和风险的判断。同样的利润,在不同的经济环境、行业阶段和市场情绪下,可能对… · 2026/9/24 17:26:48
液冷服务器渗透率2027年破50%?产业链谁在受益 中商产业研究院预计中国液冷服务器渗透率2027年有望突破50%,从2021年不足3%到2027年过半,六年翻十几倍。产业链受益顺序是:最先受益的是液冷板/换热器等核心部件,其次是冷却液、管路、CDU等配套,最后是运维和改造服务。… · 2026/9/24 17:26:48
springboot太原青年背包客深度游小程序20606-计算机课程设计、毕业设计 前言
✨ 博主介绍:一线全栈工程师,毕设实战引路人。技术栈覆盖Java、Python、C#、PHP、Node.js及UniApp跨端开发,擅长多语言项目落地与架构设计。持续分享毕设源码、开题报告、技术选型心得与职场踩坑经验。用工程化思维写代码,帮… · 2026/9/24 17:26:48
python如何反编译工具 开头段落反编译工具的主要作用, 是把已经编译好的字节码, 也就是通常说的.pyc文件, 还原成能够让人看出意思的源代码。市面上有很多种反编译工具都在被使用着, 例如人们提到的、还有pycdc等这几类, 它们能够让程序员从那些已经变得难以直接阅读的编译后文件里, 把原本清晰的源代… · 2026/9/24 17:58:25
4.3 pycharm 配置Qt Designer、PyUIC 一、这是一个关于基础方面的简易介绍。/ PyQt它本身是一个程序开发框架, 这个框架其实就是C语言那边的那个QT的一个实现版。在咱们去说那个PyQt框架之前, 呢, 还是得先把QT是个什么玩意, 还有GUI这个东西到底是啥, 给大伙简单介绍介绍。Qt 它属于那种跨平台的C图形用户界面应用… · 2026/9/24 17:58:25
非全硕士毕业有派遣证吗?2026毕业证、报到证与毕业流程详解 “非全毕业有没有派遣证(报到证)?”——这个问题要先纠正一个前提:就业报到证从 2023 年起已经全国取消发放了,全日制和非全日制都不再有。
先给结论:非全硕士毕业拿的是毕业证加学位证(双证&am… · 2026/9/24 17:58:25
216. 组合总和 III 找出所有相加之和为 n 的 k 个数的组合,且满足下列条件:
只使用数字1到9 每个数字 最多使用一次 返回 所有可能的有效组合的列表 。该列表不能包含相同的组合两次,组合可以以任何顺序返回。
示例 1:
输入: k = 3, n = 7 输出: [[1,2,4]] 解释: 1 + 2 + 4 = 7 没有其他符合… · 2026/9/24 17:58:25
2026论文爆款降AI率平台大曝光:三步操作让AI痕迹消失无踪 2026年的学术圈,仿佛一夜之间被按下了加速键。曾经大家还在为查重率焦头烂额,如今却已经全面陷入“降AI率”的生死战。随着AI检测技术不断升级,高校的审核标准也愈发严苛,论文不仅要过查重关,还得在AIGC检测中全身而退… · 2026/9/24 17:58:25
选择深圳少儿英语启蒙机构,从课后还愿不愿意碰英语看启蒙效果 家长试听时往往关注课堂内的事——老师活不活泼、孩子开不开心、一节课记住了几个词。但一个更容易被忽略、却更能说明问题的观察点是:下课之后,孩子还愿不愿意主动碰英语?这个问题的价值在于,少儿英语启蒙机构课堂上的热闹可以是… · 2026/9/24 17:58:19
基于YOLOv8的渔船作业监控系统:从环境搭建到边缘部署全流程 简介:这是一套面向计算机、人工智能、自动化等专业学生与教师的毕业设计级项目资源,围绕YOLOv8实现渔船作业监控系统,可用于毕设、课程设计、大作业或项目立项演示。压缩包共97个文件,约24.21MB,以70个Python源码文件为… · 2026/9/24 0:00:13
1D-CNN时间序列建模实战:从Conv1d原理到工业落地 简介:面向时间序列数据建模的一维卷积神经网络完整实现,适合深度学习入门者及需要快速验证时序模型的研究者,能够从音频、文本、传感器或股价等序列中挖掘局部特征与时间依赖。压缩包体积很小,只有3KB,内含3个Python脚… · 2026/9/24 0:00:26
柔软的L:汉语语流中被忽视的舌肌张力控制 1. 这个“L”不是字母表里的L,而是舌尖上的L最近在几个方言群和语音教学社群里,反复看到有人发一句:“也说字母L:柔软的长舌”。初看以为是英语发音课笔记,点开才发现全是方言爱好者、播音系学生、语言康复师甚至戏曲演… · 2026/9/24 0:00:44