深度学习:TextCNN

版权声明:本文为博主皮皮http://blog.csdn.net/pipisorry原创文章,未经博主允许不得转载。 https://blog.csdn.net/pipisorry/article/details/85076712

        对于文本分类问题,常见的方法无非就是抽取文本的特征,比如使用doc2evc或者LDA模型将文本转换成一个固定维度的特征向量,然后在基于抽取的特征训练一个分类器。 然而研究证明,TextCnn在文本分类问题上有着更加卓越的表现。

基本的cnn可以参考下[深度学习:卷积神经网络CNN]。

TextCnn的结构

        有几篇文章都是textcnn,模型结构类似。其中《Convolutional Neural Networks for Sentence Classification》给出了基本结构,《A Sensitivity Analysis ...》专门做了各种控制变量的实验对比。

Convolutional Neural Networks for Sentence Classification》[1]模型示意图

A Sensitivity Analysis ...》[2]模型示意图

1. 嵌入层(embedding layer)

        textcnn使用预先训练好的词向量作embedding layer。对于数据集里的所有词,因为每个词都可以表征成一个向量,因此我们可以得到一个嵌入矩阵MM, MM里的每一行都是词向量。这个MM可以是静态(static)的,也就是固定不变。可以是非静态(non-static)的,也就是可以根据反向传播更新。

多种模型:Convolutional Neural Networks for Sentence Classification文章中给出了几种模型,其实这里基本都是针对Embedding layer做的变化。

CNN-rand

        作为一个基础模型,Embedding layer所有words被随机初始化,然后模型整体进行训练。

CNN-static

        模型使用预训练的word2vec初始化Embedding layer,对于那些在预训练的word2vec没有的单词,随机初始化。然后固定Embedding layer,fine-tune整个网络。

CNN-non-static

        同(2),只是训练的时候,Embedding layer跟随整个网络一起训练。

CNN-multichannel

        Embedding layer有两个channel,一个channel为static,一个为non-static。然后整个网络fine-tune时只有一个channel更新参数。两个channel都是使用预训练的word2vec初始化的。

2. 卷积池化层(convolution and pooling)

卷积(convolution)

        输入一个句子,首先对这个句子进行切词,假设有s个单词。对每个词,跟句嵌入矩阵M, 可以得到词向量。假设词向量一共有d维。那么对于这个句子,便可以得到s行d列的矩阵AϵRs×d. 
我们可以把矩阵A看成是一幅图像,使用卷积神经网络去提取特征。由于句子中相邻的单词关联性总是很高的,因此可以使用一维卷积。卷积核的宽度就是词向量的维度d,高度是超参数,可以设置。 
现在假设有一个卷积核,是一个宽度为d,高度为h的矩阵w,那么w有h∗d个参数需要被更新。对于一个句子,经过嵌入层之后可以得到矩阵AϵRs×d。 A[i:j]表示A的第i行到第j行, 那么卷积操作可以用如下公式表示:

        叠加上偏置b,在使用激活函数f激活, 得到所需的特征。公式如下: 

        对一个卷积核,可以得到特征cϵRs−h+1, 总共s−h+1个特征。我们可以使用更多高度h不同的卷积核,得到更丰富的特征表达。

池化(pooling)

        不同尺寸的卷积核得到的特征(feature map)大小也是不一样的,因此我们对每个feature map使用池化函数,使它们的维度相同。最常用的就是1-max pooling,提取出feature map照片那个的最大值。这样每一个卷积核得到特征就是一个值,对所有卷积核使用1-max pooling,再级联起来,可以得到最终的特征向量,这个特征向量再输入softmax layer做分类。这个地方可以使用drop out防止过拟合。

            MaxPooling Over Time

        CNN中采用Max Pooling操作有几个好处:首先,这个操作可以保证特征的位置与旋转不变性,因为不论这个强特征在哪个位置出现,都会不考虑其出现位置而能把它提出来。但是对于NLP来说,这个特性其实并不一定是好事,因为在很多NLP的应用场合,特征的出现位置信息是很重要的,比如主语出现位置一般在句子头,宾语一般出现在句子尾等等。

        其次,MaxPooling能减少模型参数数量,有利于减少模型过拟合问题。因为经过Pooling操作后,往往把2D或者1D的数组转换为单一数值,这样对于后续的Convolution层或者全联接隐层来说无疑单个Filter的参数或者隐层神经元个数就减少了。

        再者,对于NLP任务来说,可以把变长的输入X整理成固定长度的输入。因为CNN最后往往会接全联接层,而其神经元个数是需要事先定好的,如果输入是不定长的那么很难设计网络结构。

        但是,CNN模型采取MaxPooling Over Time也有缺点:首先特征的位置信息在这一步骤完全丢失。在卷积层其实是保留了特征的位置信息的,但是通过取唯一的最大值,现在在Pooling层只知道这个最大值是多少,但是其出现位置信息并没有保留;另外一个明显的缺点是:有时候有些强特征会出现多次,出现次数越多说明这个特征越强,但是因为Max Pooling只保留一个最大值,就是说同一特征的强度信息丢失了。

pooling的几个改进:

K-MaxPooling:取所有特征值中得分在Top –K的值,并保留这些特征值原始的先后顺序,即多保留一些特征信息供后续阶段使用。

Chunk-MaxPooling:把某个Filter对应的Convolution层的所有特征向量进行分段,切割成若干段后,在每个分段里面各自取得一个最大特征值,比如将某个Filter的特征向量切成3个Chunk,那么就在每个Chunk里面取一个最大值,于是获得3个特征值。因为是先划分Chunk再分别取Max值的,所以保留了比较粗粒度的模糊的位置信息;当然,如果多次出现强特征,则也可以捕获特征强度。至于这个Chunk怎么划分,可以有不同的做法,比如可以事先设定好段落个数,这是一种静态划分Chunk的思路;也可以根据输入的不同动态地划分Chunk间的边界位置,可以称之为动态Chunk-Max方法。Event Extraction via Dynamic Multi-Pooling Convolutional Neural Networks这篇论文提出的是一种ChunkPooling的变体,就是动态Chunk-Max Pooling的思路,实验证明性能有提升。Local Translation Prediction with Global Sentence Representation 这篇论文也用实验证明了静态Chunk-Max性能相对MaxPooling Over Time方法在机器翻译应用中对应用效果有提升。

K-Max Pooling是一种全局取Top K特征的操作方式,而Chunk-Max Pooling则是先分段,在分段内包含特征数据里面取最大值,所以其实是一种局部Top K的特征抽取方式。

[自然语言处理中CNN模型几种常见的Max Pooling操作]

模型结构的示例分析

分析一下《A Sensitivity Analysis ...》[2]模型示意图:

word embedding的维度是5,对于句子 i like this movie very muc,转换成矩阵AϵR7×5;
有6个卷积核,尺寸为(2×5), (3×5), (4×5),每种尺寸各2个,A分别与以上卷积核进行卷积操作(这里的Stride Size相当于等于高度h);

再用激活函数激活,每个卷积核得到了特征向量(feature maps);
使用1-max pooling提取出每个feature map的最大值;

然后在级联得到最终的特征表达;
将特征输入至softmax layer进行分类, 在这层可以进行正则化操作( l2-regulariation)。

-柚子皮-

实验参数分析

根据《A Sensitivity Analysis...》[2]的实验对比:

(1)初始化词向量:一般不直接使用One-hot。除了随机初始化Embedding layer的外,使用预训练的word2vec、 GloVe初始化的效果都更加好。非静态的比静态的效果好一些。

(2)卷积核的尺寸filter_sizes:影响较大,一般取1~10,对于句子较长的文本,则应选择大一些。

(3)卷积核的数量num_filters(对每个巻积核尺寸来说):有较大的影响,一般取100~600 ,同时一般使用Dropout(0~0.5)。

(4)激活函数:一般选用ReLU 和 tanh。

(5)池化选择:1-max pooling。

(6)Dropout rate / dropout_keep_prob:随着feature map数量增加,性能减少时,试着尝试大于0.5的Dropout。

(7)评估模型性能时,记得使用交叉验证。

(7)正则项对最终模型性能的影响很小。

其它的训练参数:batch_size:64;num_epochs:10;每checkpoint_every:100轮便保存模型;仅保存最近num_checkpoints:5次模型

from: https://blog.csdn.net/pipisorry

ref: [TextCnn原理及实践]

[自然语言中的CNN--TextCNN(基础篇)]

Convolutional Neural Networks for Sentence Classification2014》[1]

A Sensitivity Analysis of (and Practitioners’ Guide to) Convolutional Neural Networks for Sentence Classification》[2]

[Understanding Convolutional Neural Networks for NLP]

猜你喜欢

转载自blog.csdn.net/pipisorry/article/details/85076712