任务描述: 自动摘要是指给出一段文本,我们从中提取出要点,然后再形成一个短的概括性的文本。自动的文本摘要是非常具有挑战性的,因为当我们作为人类总结一篇文章时,我们通常会完整地阅读它以发展我们的理解,然后写一个摘要突出其要点。由于计算机缺乏人类知识和语言能力, 它使自动文本摘要成为一项非常困难和艰巨的任务。自动摘要通常分为抽取式摘要和生成式摘要,区别在于抽取摘要选择原文中若干句子作为只要,而生成式摘要利用文本生成技术根据原文生成摘要,这个摘要会出现原文中没有出现过的句子和词。生成式方法则应用先进的自然语言处理的算法,通过转述、同义替换、句子缩写等技术,生成更凝练简洁的摘要。比起抽取式,生成式更接近人进行摘要的过程。历史上,抽取式的效果通常优于生成式。生成式文本摘要以一种更接近于人的方式生成摘要,这就要求生成式模型有更强的表征、理解、生成文本的能力。传统方法很难实现这些能力,而近几年来快速发展的深度神经网络因其强大的表征(representation)能力,提供了更多的可能性,在图像分类、机器翻译等领域不断推进机器智能的极限。借助深度神经网络,生成式自动文本摘要也有了令人瞩目的发展,不少生成式神经网络模型(neural-network-based abstractive summarization model)在DUC-2004测试集上已经超越了最好的抽取式模型。这部分文章主要介绍生成式神经网络模型的基本结构及最新成果。伴随深度神经网络的兴起和研究,基于神经网络的生成式文本摘要得到快速发展,并取得了不错的成绩。 本教程介绍一种seq2seq+attention 生成式摘要算法。 ### 数据集:使用gigaword数据集,但是由于数据集太过庞大, 只抽取了部分数据,其中训练集20000个数据,验证集1000个数据,测试集1000个数据。本文所阐述的模型主要是借鉴下边这篇机器翻译作为基础来学习生成式文本摘要,两个任务很类似。
可参考学习的论文:谷歌发表的关于机器翻译的论文
1. encoder-decoder
encoder-decoder框架的工作机制是:先使用encoder,将输入编码到语义空间,得到一个固定维数的向量,这个向量就表示输入的语义;然后再使用decoder,将这个语义向量解码,获得所需要的输出,如果输出是文本的话,那么decoder通常就是语言模型。
这种机制的优缺点都很明显,优点:非常灵活,并不限制encoder、decoder使用何种神经网络,也不限制输入和输出的模态(例如image caption任务,输入是图像,输出是文本);而且这是一个端到端(end-to-end)的过程,将语义理解和语言生成合在了一起,而不是分开处理。缺点的话就是由于无论输入如何变化,encoder给出的都是一个固定维数的向量,存在信息损失;在生成文本时,生成每个词所用到的语义向量都是一样的,这显然有些过于简单。
2. attention mechanism 注意力机制
为了解决上面提到的问题,一种可行的方案是引入attention mechanism。所谓注意力机制,就是说在生成每个词的时候,对不同的输入词给予不同的关注权重。谷歌博客里介绍神经机器翻译系统时所给出的动图形象地展示了attention:
3.Seq2Seq结构 以机器翻译为例,假设我们要将 How are you 翻译为 你好吗,模型要做的事情 如下图:
3.1图解:
(1)上图中,LSTM Encoder 是一个 LSTM 神经元,Decoder 是另一个 LSTM 神经元,Encoder 自身运行了 3 次,Decoder 运行了 4 次。
(2)可以看出,Encoder 的输出会被抛弃,我们只需要保留隐藏状态(即图中 EN 状态)作为下一次 Encoder 的状态输入。
(3)Encoder 的最后一轮输出状态会与 Decoder 的输入组合在一起,共同作为 Decoder 的输入。
(4)而 Decoder 的输出会被保留,当做下一次的输入。注意,这是说的是预测时的情况,在训练时一般会用真正正确的输出序列内容,而预测时会用上一轮 Decoder 的输出。
(5)给 Decoder 的第一个输入是 <S>,这是我们指定的一个特殊字符,它用来告诉 Decoder,你该开始输出信息了。
(6)而最末尾的 <E>,也是我们指定的特殊字符,它告诉我们,句子已经要结束了,不用再运行了。
3.2、伪数学
从更高层的角度来看算法,整个模型也无非是一种从输入到输出的函数映射。
我们已知的输入数据是 How are you,我们希望的输出是 你好吗,模型学习了下面这些函数映射,组成了一个单射函数:
{How, are, you, <S>} {你}
{How, are, you, <S>, 你} {好}
{How, are, you, <S>, 你, 好} {吗}
{How, are, you, <S>, 你, 好, 吗} {<E>}
原文链接:https://blog.youkuaiyun.com/weixin_38477351/article/details/108814274
以上是理论部分讲解,可以根据相关的模型和动态图了解到attetnion机制是如何在Seq2Seq模型上进行计算注意力的。
4、关于文本摘要的代码,主要包括五部分,数据的准备、模型的结构以及定义、模型的训练、模型的预测、以及模型评估
##模型的说明,数据的准备以及环境的准备
### 任务描述: 自动摘要是指给出一段文本,我们从中提取出要点,然后再形成一个短的概括性的文本。自动的文本摘要是非常具有挑战性的,因为当我们作为人类总结一篇文章时,我们通常会完整地阅读它以发展我们的理解,然后写一个摘要突出其要点。由于计算机缺乏人类知识和语言能力,
它使自动文本摘要成为一项非常困难和艰巨的任务。自动摘要通常分为抽取式摘要和生成式摘要,区别在于抽取摘要选择原文中若干句子作为只要,而生成式摘要利用文本生成技术根据原文生成摘要,这个摘要会出现原文中没有出现过的句子和词。
本教程介绍一种seq2seq+attention 生成式摘要算法。
### 数据集:使用gigaword数据集,但是由于数据集太过庞大,
只抽取了部分数据,其中训练集20000个数据,验证集1000个数据,测试集1000个数据。
### 运行环境
Python==3.6
numpy==1.18.0
pandas==0.24.2
torch==1.0.0
torchtext==0.4.0
spacy==2.1.8
rouge==1.0.0
尤其要注意mask矩阵时使用的真正的长度-有相应的代码
本次运行的是短文本生成摘要
基于seq2seq+attention
模型的基本原理和机器翻译相同,是生成式的
/* 模型主要结构部分 */
# 统一导入工具包
# 使用pip命令安装指定版本工具包
# !pip install numpy==1.18.0 pandas==0.24.2 torch==1.0.0 torchtext==0.4.0 spacy==2.1.8 rouge==1.0.0
"""
import torch
import torch.nn as nn
import torch.optim as optim
import torch.nn.functional as F
from torchtext.datasets import Multi30k
from torchtext.data import Field, BucketIterator, TabularDataset, Iterator
import pandas as pd
import spacy
import numpy as np
import random
import math
import time
# 全局初始化配置参数。固定随机种子,使得每次运行的结果相同
#SEED = 22
random.seed(22)
np.random.seed(22)
torch.manual_seed(22)
if torch.cuda.is_available():
torch.cuda.manual_seed_all(22)
torch.backends.cudnn.deterministic = True
#1.数据准备¶使用gigaword数据集本教程的实验数据,并对数据进行预处理,主要包含以下步骤:
#(1) 数据整理
#(2) 数据说明
#(3) 数据预处理:构建分词函数、构件预处理格式、载入数据、构建数据迭代器、构建词表。
#1.1数据整理
#使用gigaword数据集,但是由于数据集太过庞大,只抽取了部分数据,其中训练集20000个数据,验证集1000个数据,测试集1000个数据。其中训练集用以训练模型,
#验证集用以调整训练参数,测试集用以测试模型。
#完整的数据集详见 https://github.com/harvardnlp/sent-summary ,
#需要处理成data_train_path中相同的csv格式。
#数据处理、分词
data_train_path = 'datasets/train.csv'
data_val_path = 'datasets/val.csv'
data_test_path = 'datasets/test.csv'
#1.2数据说明
# 用pandas包读取csv格式的数据,展示数据格式,其中‘document’为原文,‘summary’为原文的摘要
data_train = pd.read_csv(data_train_path,encoding='utf-8')
print(data_train.head())
#1.3数据预处理
#为了方便模型读入数据,需要对模型进行预处理,包括:
#(1)构建分词函数
#(2)构建预处理格式
#(3)载入数据
#(4)构建数据迭代器
#(5)构建词表
#1.3.1 构建分词函数¶分词是自然语言处理的基础,需要识别文本中有哪些词组,
# 方便后续的处理。由于英文以空格的形式隔开,每个单词都是可以独立的词组,因此可以直接用空格符分词,但是为了识别文本中的所有短语词组以得到更准确的摘要结果,
# 这里使用了spacy包里的tokenizer工具对文本中的短语进行分词。
#spacy在使用前下载安装语言包,在终端命令行中输入:
#python -m spacy download en
# 载入spacy的英文处理包
# import en_core_web_md
spacy_en = spacy.load('en_core_web_md')
# 构建分词函数,返回文本里包含的所有词组的列表
def tokenize(text):
return [tok.text for tok in spacy_en.tokenizer(text)]
#1.3.2 构建数据预处理格式
在自然语言处理的预处理中有很多优秀的工具包,可以节省开发人员的开发成本,在这里我们使用torchtext,t