其他

8个步骤,上手解决90%的 NLP 问题

2018-02-04 Emmanuel Ameisen 集智AI学园

前言

如何利用机器学习来理解和利用文本?这是一份入门指南。


自然语言处理技术覆盖领域极广,重要的应用包括:

  • 识识别不同的用户/客户群(例如预测流失率、生命周期、产品偏好)

  • 准确检测和提取用户反馈(正面和负面评价、衣服尺寸之类的特定属性)

  • 根据用户意图将文本分类(例如区分普通问题和紧急求助)


如何利用机器学习来理解和利用文本?本文给出了八个具体步骤

  1. 收集数据

  2. 清理数据

  3. 找到好的数据表示方法

  4. 为数据分类

  5. 检查和解释数据

  6. 计算语言结构

  7. 理解语义

  8. 使用端到端的方式训练语法特征


阅读本文,你将了解到:

  • 如何收集、准备和检查数据

  • 如何建立简单模型,并在必要时建立深度学习模型

  • 如何理解和解释模型,确保你捕捉到信息而非噪音


1.数据收集


数据样本


每个机器学习问题都始于数据,例如电子邮件、帖子或推文。文本信息常见来源包括:

  • 产品评论(亚马逊等网络商店中)

  • 用户自生产内容(推特、Facebook 帖子、Stack Overflow 问答)

  • 故障排除(客户请求、提供票据、聊天记录)


数据集:社交媒体灾难


本文使用由 CrowdFlower 提供的名为“社交媒体中的灾难”的数据集。数据集整理者在推特上检索了超过一万条包含“着火”、“隔离”和“混乱”等关键词的推文,然后检查这些推文是否是指灾难事件(排除用这些词开玩笑、写影评等情况)。


检测出哪些推文和灾难事件有关,排除玩笑、电影等实际上不相关的话题。这里面的挑战是,无论是否与灾难相关,这些推文有着相同的检索关键词,所以必须使用更加微妙的区别来区分它们。


在本文后续部分,我们将把和灾难有关的推文称为“灾难事件”,其他推文称为“与灾难无关的事件


标签


样本数据中的推文都是人工标记过的,所以我们知道每条推文是属于“灾难事件”还是“与灾难无关的事件”。正如 Richard Socher 在下图推文中所说,相比于优化一个复杂的无监督方法,找到并标记足够多的数据来训练模型通常更快、更简单,成本更低。


Richard Socher,Salesforce 公司首席科学家,斯坦福大学计算机系兼职教授


2:数据清洗


机器学习首要原则:“模型性能受制于数据好坏”。


数据科学家的一个关键技能就是知道下一步是该处理数据还是去研究模型。一个好的经验法则是,先查看数据再清洗数据。一个干净的数据集能让模型学习到有意义的特征,而不是学到过拟合的噪音。


这里有一个数据清洗方法清单:

  1. 删除无关字符,例如非字母或数字的字符串

  2. 将文本分离成单独文字来标记解析

  3. 删除无关词汇,例如“Twitter@”或网址

  4. 将所有字母转换为小写,以便处理“hello”、“Hello”、“HELLO”之类的单词

  5. 将拼写错误或重复拼写的单词单独表示(例如“cool”/“kewl”/“cooool”)

  6. 考虑词性还原(例如将“am”、“are”、“is”等词语统一为“be”)


数据清洗的更多细节请访问:

https://github.com/hundredblocks/concrete_NLP_tutorial/blob/master/NLP_notebook.ipynb


遵循这些步骤并检查其他错误之后,我们就有了比较干净的标签数据来训练机器学习模型了!


3:找到好的数据表示方法


机器学习模型输入的是数值。处理图像的模型,是以矩阵表示每个颜色通道中各个像素的强度。


一副笑脸,可以用一个数字矩阵表示


本文的数据集是一个句子列表,所以为了使我们的算法能从数据中学习到特征,首先要找到一种方法,把数据集转换成机器学习模型能理解的形式,比如把句子列表转换成一个数字列表。


One-hot 编码(词袋模型)


计算机表示文本的常用方法是,把每个字符单独编码成一个数字,例如 ASCII 编码。但如果把这种简单的表示形式输入到分类器中,它就得从零开始学习所有单词的结构,这太难了。所以,我们需要更巧妙的方法。


例如,我们可以为数据集中所有的单词建立一个不重复的词汇表,每个单词对应一个索引值。那么,数据集中的每句话,都可以表示成一个和词汇表一样长的列表。列表中每个单词的索引值,就是该单词在这个句子中出现的次数。这就是所谓的 Bag of Words 词袋模型。之所以叫“词袋”,是因为它完全忽略了单词在句子中的次序,而只关心单词出现的次数。如下图所示:

将句子表示为词袋模型(bag-of-words):左边是句子,右边是对应的数字表示。向量中的每个索引值都代表一个特定的词。


可视化的词嵌入模型


在“社交媒体灾难”数据样本中,有20000个单词,这意味着每个句子都会被表示成一个长度为20000的向量。该向量的大部分元素是0,因为每个句子都只是词汇表的一个非常小的子集。


为了了解词嵌入模型能否捕捉到问题相关的信息(即推文是否与灾难有关),可以将其可视化,看看类别之间是否明显分离。由于词表的词汇量很大,并且20000个维度的可视化是不可能的,所以采用 PCA (一种将特征降维的技术),将数据投射到两个维度。结果如下:


词嵌入模型的可视化


词嵌入模型的可视化结果显示,两类数据的分离效果不佳。这种效果可能就是我们词嵌入的特征,也可能是由于降维导致的。为了验证词袋模型学到的特征是否有用,我们可以用词袋模型来训练一个分类器


4.分类器


面对机器学习问题,最好先找到能解决问题的简单工具。对数据进行分类时,往往使用逻辑回归分析的方法(Logistic Regression),以保障结果的通用性和可解释性。训练过程很简单。因为很容易从模型中提取出重要参数,所以训练结果也容易解释。


第一步是将数据分成两部分,一部分是训练集,另一部分是测试集。经过训练,该模型把推文内容归为“灾难事件”的预测,准确率达到75.4%,效果还是不错的。而把推文内容归为“与灾难无关事件”的预测,准确率只有57%。75%的精确度已经满足我们的需求。下面,我们开始试图理解这个模型。



5:检验模型


混淆矩阵


理解模型的第一步,是了解模型产生的错误分类,以及最不应该出现的错误。在我们的例子中,“误报”是指将不相关的推文分类为“灾难事件”,“漏报”是指将与灾难有关的推文归类为“与灾难无关的事件”。如果要优先处理潜在的灾难事件,那就要降低“漏报”。而如果资源受限,就要优先降低“误报”,减少错误的提醒。使用混淆矩阵可以很好地可视化这些信息,并将模型预测的结果与数据的真是标签进行比较。理想情况下,模型的预测结果与真实情况(人工标注)完全相符,这时候混淆矩阵是一条从左上角到右下角的对角矩阵。


混淆矩阵(绿色部分占比较高,蓝色部分占较低)


分类器的漏报明显多于误报,这意味着这个模型的常见错误是把灾难事件归为“与灾难无关的事件”如果误报灾难的执法成本远高于漏报灾难的损失,那我们的分类模型就是可取的。


解释和干预我们的模型


为了验证我们的模型并对其预测做出解释,我们就要看那些单词在预测中起决定性作用。如果数据有偏差,那分类器会对样本数据做出准确预测,但实际应用时效果会不理想。


下图是为“灾难事件”和“与灾难无关的事件”列了一个重要单词表。因为我们可以提取并比较模型中的预测系数,所以很容易用词袋模型和逻辑回归来找出重要的单词。


词袋:重要词汇


我们的分类器正确地找到了一些特征,比如广岛(hiroshima)和大屠杀(massacre),但也存在无意义数据的过拟合,比如 heyoo、x1392。我们当前的词袋模型处理的是一个庞大的词表,并且对所以单词一视同仁。但实际上,其中某些单词频繁出现,成了影响我们预测的噪声。接下来,我们尝试一种方法来表示单词的频率,看能否从数据中获得更多有用信号。


6:词汇结构的统计


TF-IDF嵌入模型


为了让模型专注于学习有意义的单词,可以使用 TF-IDF (词频-逆文档频率嵌入模型)评估词袋模型。TF-IDF 对单词在数据中的稀疏程度来评估其重要性,对那些出现频率高但只是增加噪声的单词进行降权处理。下图是 TF-IDF 嵌入模型的 PCA 映射:


将TF-IDF嵌入模型可视化


从图中看到,两种颜色之间有明显的分区了,这让分类器更容易区分两个类别。让我们看看这是否会带来更好的表现。


用 Logistic 逻辑回归训练新嵌入的模型 ,结果显示,模型把推文内容归为“灾难事件”的预测,准确度达到了76.2%,比起之前的75%稍有提高。


这是非常小的改进,但模型能否因此学到更重要的词汇呢?如果模型在预测时跳过了“陷阱词汇”因而获得更好结果,那才能说 TF-IDF 对模型提升有帮助。


TF-IDF嵌入模型:重要单词


从新的重要词汇列表可以看到,新模型学到的重要词汇看起来与事件分类的关系更密切了!尽管测试集的指标只是略有增加,但是模型使用的重要关键词更靠谱了,所以这个新模型会让用户体验更好。


7:利用语义


Word2Vec


使用了 TF-IDF 技术的新模型能够学习到信号强烈的单词。但是如果部署这个模型,很可能会遇到一些在训练集中没有的词汇。训练集训练出的模型无法对这样的新数据进行分类,即使模型曾经在训练集中遇到过相似的词。


为了解决这个问题,就要捕捉单词的含义。例如,模型需要理解“good”在语义上与“positive”更接近,而不是和“apricot(杏)”或者“continent(大陆)”更接近。这里用来捕捉语义的工具就是 Word2Vec。


使用预先训练好的词汇


Word2Vec 是一种为每个单词生成词向量的技术。通过阅读大量文本,它能够学到并记住那些倾向于在相似语境中出现的词汇。经过足够多的数据训练,词汇表中的每个单词都会生成一个300维的向量,由意思相近的单词组成。


论文《Efficient Estimation of Word Representations in Vector Space

》的作者 Tomas Mikolov 开源一个 Word2Vec 模型。这个模型已经在一个非常大的语料库上经过了预训练,我们可以把这个模型的一些语义知识纳入我们的模型。预训练向量的资源地址是:

https://github.com/hundredblocks/concrete_NLP_tutorial


句子的表示


为分类器获得一个句子嵌入的快速方法是对句中所有单词的 Word2Vec 分数求平均。这中方法和之前的词袋模型是类似,区别是这次我们仅仅忽略了句子语法,而保留了句子的一些语义信息。

Word2vec 模型的句子嵌入


用前文技术对新嵌入模型可视化,结果如下:

Word2Vc嵌入模型的可视化结果


相比于上一个模型,这里的两组颜色区分更加明显,Word2Vec 可以让分类器更好地分类。再次使用 Logistic 回归方法训练模型之后,模型把推文内容归为“灾难事件”的预测准确率达到了77.7%,又创新高!


复杂性/可解释性的权衡


由于我们这次的 Word2Vec 嵌入没有像之前的模型那样把每个单词表示成一维向量,所以很难看出哪些单词对分类结果是重要的。尽管仍然可以使用  Logistic 回归系数,但这些系数仅仅和嵌入的300个维度有关,而和词表中词汇索引值无关。


模型准确率提高有限,但却牺牲了所有的可解释性,似乎得不偿失。不过,对于更复杂的模型,我们可以利用 LIME 之类的“黑盒解释器(black box explainers)”来解释分类器的工作。


LIME


LIME是Github上的一个开源软件包,项目地址:

https://github.com/marcotcr/lime


LIME 黑盒解释器允许用户通过观察输入的扰动(比如删除句中某个单词)并观察扰动引起的变化,来分析一个分类器的预测结果是如何变化的。


来看看它对我们数据集中几个句子的解释:


这句话中,选出了正确的灾难词汇,并把句子归类为“灾难事件”


但在这一句中,单词对分类的影响似乎不太明显


但是,我们没有时间去探索数据集中的大量样本。我们要做的是在测试集的代表性样本上运行 LIME,分析哪些词汇对于分类预测的影响更大。这样一来,我们可以像之前的模型一样,评估出重要单词,并验证模型的预测结果。


Word2Vec 的重要单词


Word2Vec 模型提取出了高度相关的词,这意味着它做出了可解释性更强的判断。上面这些词汇与事件性质的相关性是最高的,我们更愿意把它们添加到实际应用中。


8:使用端到端(end-to-end)方式学习语法特征


前面介绍了快速高效地获得句子嵌入的方法,然而由于省略词汇的顺序,我们也忽略了句子中所有的语法信息。如果简单方法给出的结果还不够让人满意,那我们就用更复杂的模型:把整个句子作为输入并预测标签,而不用中间表示。常见的做法是,使用 Word2Vec 或者 GloVe、CoVe 等方法,把一个句子作为词向量的序列。这就是下面要做的:


高效的端到端的训练体系结构


用于句子分类的卷积神经网络训练速度很快。卷积神经网络(CNN)作为一种入门级的深度学习框架效果很不错,虽然 CNN 主要以在图像处理方面的出色表现而著称,但在文本相关的任务上也有出色的表现,而且比大多数复杂的 NLP 方法(如 LSTMs、Encoder/Decoder)训练更快。CNN 能够考虑单词的顺序,能很好地学习到句子中哪些单词的序列特征影响到目标预测。比如它可以区分出“Alex eats plants”与“Plants eat Alex”之间差异。


相比以往的方法,end-to-end 模型的训练不要要太多工作就能取得不错的效果,准确率达到了79.5%!具体代码参见:

https://github.com/hundredblocks/concrete_NLP_tutorial/blob/master/NLP_notebook.ipynb


当然与前面步骤一样,紧接着就要使用上述方法对这个模型的预测做出解释,以确认它是否足够好。经过上面的讨论,你应该可以自己解决这个问题了。


最后的笔记


回顾一下我们成功使用的方法:

  • 从一个简单快速的模型开始

  • 对模型的预测作出解释

  • 了解它所犯错误的种类

  • 根据以上知识判断下一步做什么:处理数据,还是寻找复杂的模型


虽然上述方法用于本文特定的例子——使用适当模型理解和利用短文本(推文),但这种思想适用于各类问题。希望这篇文章对你有帮助,也欢迎提出意见和问题!





本文由集智小仙女编译整理自 insightdatascience 博客:

原题:How to solve 90% of NLP problems: a step-by-step guide

地址:https://blog.insightdatascience.com/how-to-solve-90-of-nlp-problems-a-step-by-step-guide-fda605278e4e



关注集智AI学园公众号

获取更多更有趣的AI教程吧!

搜索微信公众号:swarmAI

集智AI学园QQ群:426390994

学园网站:campus.swarma.org

 商务合作|zhangqian@swarma.org     

投稿转载|wangjiannan@swarma.org



您可能也对以下帖子感兴趣

文章有问题?点此查看未经处理的缓存