1. NLP

[TOC]


1.1. 零、常用知识点

  • 单词 -> 短语 -> 从句 -> 句子 -> 文档/语料库
    • 单词/标识(token):是具有一定的句法语义,且独立的最小文本成分。
  • 词:一门独立语言中的最小单位。
  • 词素:具有独特意义的最小语言单位,但它不是独立的,一个单词可以由几个词素组成。
  • 词元:是一组词的基本形式。
  • 词位{eating,ate,eats} 包含3种词性,他们的词元是eat。
  • 词性标注(POS):Part-Of-Speech tagging
  • 命名实体识别(NER):Named Entity Recognition
  • 过拟合:模型学习能力太强,以至于把噪声数据的特征也学习到了,导致模型泛化能力下降,在训练集上表现很好,但是在测试集上表现很差。
  • 欠拟合:就是模型不能够很好地拟合数据,表现在模型过于简单。
  • 有汉字成词能力的 HMM 模型
  • NLP工具小清单
    • GATE、Mallet、Open NLP、UIMA、Stanford toolkit、Gensim、NLTK
  • NLP常用python库
    • NLTK
    • pattern.en:包含文本分析的大多实用工具。
    • gensim:具有一套丰富的语义分析功能,包括主题建模和相似性分析。word2vec模型的py接口。
    • textblob:文本处理,短语提取,分类,pos标注,文本翻译,情感分析
    • spacy:提供工业级NPL功能
    • 其他:不是专门用于文本分析的框架和库,但当相对文本使用机器学习时,是有用的
      • scikit-learn
      • numpy
      • scipy stack
      • 深度学习和基于张量的库:theano,tensorflow,keras

1.2. 一、语料预处理

在一个完整的中文NLP应用中,语料预处理占到整个工作量的50%-70%。

1.2.1. 1. 数据洗清

把不感兴趣的、视为噪音的内容清洗删除。主要有:

  • 链接
  • 以@开头的用户名

人工去重、对齐、删除和标注等,或者规则提取内容、正则表达式匹配、根据词性和命名实体提取、编写脚本或者代码批处理等。

1.2.2. 2. 分词

在进行分词前,需要进行命名实体提取,这样分词更准确。

常见的分词算法:

  • 基于字符串匹配的分词方法:在已有字典的基础上,按照指定的规则进行匹配,直到完成规则中的“最大”匹配,则识别出一个词。按照匹配的方向不同可以分为:正向最大匹配、逆向最大匹配、双向最大匹配。
  • 基于理解的分词方法:利用计算机模拟人对文本的理解,结合语义、句法等因素处理文本,从而实现分词。该方法需要大量的语言知识,由于中文文本自身的复杂性,该方法目前还难以实施。
  • 基于统计的分词方法:计算机通过计算字符串在语料库的出现频率对其是否构成词进行判断。使用最为广泛。

当前中文分词算法的主要难点有歧义识别和新词识别。

(0) 常用的中文分词工具

常见的中文分词实现:中科院计算所 NLPIR、哈工大 LTP、清华大学 THULAC 、斯坦福分词器、Hanlp 分词器、jieba 分词、IKAnalyzer 等。

常用的分词词典:《同义词词林(扩展版)》、《现代汉语语义词典》、《现代汉语语义词典》、《知网》、《人民日报语料库》等。

ICTCLAS 分词系统,其主要思想是通过隐马尔可夫模型进行分词,实现已有词识别、简单未登录词识别、词性标注等功能,提高了分词的准确性和效率。

NLPIR 分词工具也是以此为基础开发的,缺点是标准版本需要付费,提供的接口难以适用于JAVA。

THULAC 分词工具是由清华大学自然语言处理与社会人文计算实验室研发,具备分词和词性标注等功能,计算能力强、速度快、准确率高,缺点是只支持UTF8 编码的中文文本。

分词改进方向:

  1. 提高未登录词的识别率
  2. 歧义消除
  3. 提高分词速度

在目前实际应用中,广泛使用的分词手段还是已有的分词工具进行初步分词,再结合未登录词识别算法进一步进行操作。

《00 中文文本分类方法综述_于游》

​ 针对未登录词识别问题,文献[8]提出网络舆情中的新词识别方法,利用网络舆情中未被词典收录的主题词的局部高频这一特性,通过计算异常分词与周围分词之间的粘结度,识别出未被词典收录的主题词,但该方法仅仅通过单个字分词对异常分词进行判断和召回。文献[9]针对短文本的特点,通过对条件随机场中的标记选择和特征做出了优化,提出一种基于条件随机场的中文文本分词方法,该算法可有效解决传统CRF 算法标记冗余的问题,并有良好的未登录词识别效果,但由于标记选择的原因,其在不同长度词的识别上有一定的局限。文献[10]对未登录词识别方法做了进一步改进,利用互信息改进算法,提出一种非监督的词识别方法,结合规则,可以在大规模语料中识别出指定长度的新词。文献[11]和文献[12]都通过LSTM 记忆单元和神经网络模型,对分词方法进行了改进,改进后的方法有效利用序列长距离信息和上下文信息,但算法复杂且神经网络具有黑箱特性,不易于理解。

(1) jieba分词

Jieba 分词工具是基于Trie 树结构采用动态规划查找最大概率路径的方法得到分词结果,并采用基于隐马尔可夫模型和Viterbi 算法进行未登录词识别,是国内使用最多的中文分词工具。缺点是在未登录词识别上存在缺陷,大部分需要用户手动加入词典。

jieba分词步骤:

  1. 基于统计词典,构造前缀词典,基于前缀词典对句子进行切分,得到所有切分可能,根据切分位置,构造一个有向无环图(DAG)。
  2. 基于DAG图,采用动态规划计算最大概率路径(最有可能的分词结果),根据最大概率路径分词。
  3. 对于新词(词库中没有的词),采用有汉字成词能力的 HMM 模型进行切分。

1.2.3. 3. 去停用词

停用词一般指对文本特征没有任何贡献作用的字词,比如标点符号、语气助词、人称代词等。

  • 在一般性的文本处理中,分词之后,下一步就是去停用词。但是对于中文来说,是否去停用词、去除哪些停用词,是根据具体场景来决定的,比如在情感分析中,语气词、感叹号是应该保留的。

1.2.4. 4. 词性标注

给每个词或者词语打词类标签。

  • 词性标注不是必需的。比如,文本分类就不用关心词性问题,而类似情感分析、知识推理却是需要的。

词性标注方法

  • 基于规则的词性标注方法
  • 基于统计的词性标注方法

    • 基于最大熵的词性标注、基于统计最大概率输出词性、基于 HMM 的词性标注

jieba

# pos segment
# return: [jieba.posseg.pair(word, flag), ]
jieba.posseg.cut(sentence)

1.3. 二、特征工程

特征提取主要是通过属性间的关系,改变原特征空间,如组合不同属性得到新的属性。有PCA 、LDA 、SVD。

特征选择则是对原特征空间中的特征进行筛选,没有改变其原属性。有Filter 、Wrapper 、Embedded 。

两者的核心目的都是为降低特征向量维度

1.3.1. 1. 特征提取

特征提取的一般方法:

  • Filter 法:主要思想是通过对每个特征赋予权重,根据其重要程度对特征进行选择。目前常用的Filter 法主要有:基于文档频率的方法、x2统计量法、互信息方法、信息增益方法。
  • Wrapper 法:实质是将特征选择问题作为寻优的问题,通过对不同组合进行评价和比较,选择出最优的特征集合。目前常用的Wrapper 方法主要有遗传算法(GA )、粒子群优化(PSO )、优化蚁群算法(ACO )。
  • Embedded 法:通过在建立模型的过程中,筛选出对提高模型准确度最有用的特征。

(1) 词袋模型(Bag of Word, BOW)

不考虑词语顺序,直接对词语出现的次数进行统计。

统计词频这只是最基本的方式,TF-IDF 是词袋模型的一个经典用法。

(2) TF-IDF模型(Token Frequency-Inverse Document Frequency)

由词频*逆文档频率得到。

  • 词频(Token Frequency):表示词 t 在文档 d 中出现的频率。
  • 逆文档频率(Inverse Document Frequency):表示语料库中包含词 t 的文档的数目的倒数。

(3) 词向量模型

词向量就是要用某个固定维度的向量去表示单词。

将字、词语转换成向量矩阵的计算模型。

常用模型:

  • One-hot:把每个词表示为一个很长的向量。向量的维度是词表大小,其中绝大多数元素为 0,只有一个维度的值为 1,这个维度就代表了当前的词。
  • Word2Vec:将 One-Hot Encoder 转化为低维度的连续值,也就是稠密向量,并且其中意思相近的词也将被映射到向量空间中相近的位置。经过降维,在二维空间中,相似的单词在空间中的距离也很接近。
    • Word2Vec 词向量可以较好地表达不同词之间的相似和类比关系。
    • Word2Vec包含2中模型:
      • 跳字模型(Skip-Gram)
      • 连续词袋模型(Continuous Bag of Words,CBOW)
  • Doc2Vec:Doc2Vec 是 Mikolov 在 Word2Vec 基础上提出的另一个用于计算长文本向量的工具。
    • 实现方式:DBOW(Distributed Bag of Words)、 DM (Distributed Memory)。
  • WordRank
  • TextRank
  • FastText
  • GloVe

在工业界,Word2Vec 和 Doc2Vec 常见的应用有:做相似词计算;相关词挖掘,在推荐系统中用在品牌、用户、商品挖掘中;上下文预测句子;机器翻译;作为特征输入其他模型等。

1.3.2. 2. 特征选择

文本特征一般都是词语,具有语义信息,使用特征选择能够找出一个特征子集,其仍然可以保留语义信息;但通过特征提取找到的特征子空间,将会丢失部分语义信息。因此,选用特征向量,我们要找这样的向量:即使它丢失了一些语义信息,这些丢失的语义信息也不是我们需要的,或占比权重很小的。

在一个实际问题中,在构造好的特征向量中,是要选择合适的、表达能力强的特征,即与你要解决的问题最相关的特征向量。

常见的特征选择方法主要有 DF、 MI、 IG、 CHI、WLLR、WFO 六种。

1.4. 三、词法与语法分析

1.4.1. 1. 浅层分析

浅层句法分析:用来提取句子(一组单词)中的短语。

1.4.2. 2. 语法分析

(1) 依存语法(基于词的语法)

在大多数情况下,将动词视为句子的根。依存关系树不是描述句子中词的顺序,而是强调句子中词之间的关系。

from pyhanlp import HanLP
# 依存句法分析
HanLP.parseDependency(document)

(2) 成分语法(短语结构文法)

1.5. 四、模型训练

  • 朴素贝叶斯

    • ? 朴素贝叶斯应用在自然语言处理的时候,是不是只是把单词截断当作特征,全然没有考虑语序的问题啊。有没有那样的句子,比如把主谓宾调换位置,语义就变了呢?是不是朴素贝叶斯在自然语言处理方面有这种缺陷呢

  • 支持向量机(SVM)

  • 模型训练

    • 有监督和无监督等机器学习模型, 如 KNN、SVM、Naive Bayes、决策树、GBDT、K-means 等模型
    • 深度学习模型比如 CNN、RNN、LSTM、 Seq2Seq、FastText、TextCNN 等。

模型训练需注意:注意过拟合、欠拟合问题,不断提高模型的泛化能力。

过拟合解决方法:

  • 增大数据的训练量。
  • 增加正则化项,如 L1 正则和 L2 正则。
  • 特征选取不合理,人工筛选特征和使用特征选择算法。
  • 采用 Dropout 方法等。

欠拟合解决方法:

  • 添加其他特征项。
  • 增加模型复杂度,比如神经网络加更多的层、线性模型通过添加多项式使模型泛化能力更强。
  • 减少正则化参数,正则化的目的是用来防止过拟合的,但是现在模型出现了欠拟合,则需要减少正则化参数。

对于神经网络,注意梯度消失和梯度爆炸问题。

模型的评价指标

混淆矩阵:

真实情况 预测 结果
正例 负例
正例 TP(真正例) FN(假负例)
负例 FP(假正例) TN(真负例)

注:正例,是我们感兴趣的类。Positive,Negative

具体指标:

  • 错误率:分类错误的样本数占样本总数的比例。
  • 精度:分类正确的样本数占样本总数的比例。 错误率 + 精度 = 1
  • 准确率(accuracy):(TP+TN)/ALL。预测正确的占比。
  • 精确率(precision):TP/ALL。真正例占比。
  • 召回率(recall):TP/(TP+FN)。正例中有多少正例被准确预测。
  • F1 衡量:精确率与召回率的调和平均值。
  • ROC曲线:受试者工作特征(Receiver Operating Characteristic)曲线。纵轴是“真正例率”(真正例/实际正例),横轴是“假正例率”(假正例/实际负例)。
  • AUC(Area Under Curve):ROC 曲线下的面积。

ROC 曲线的意义有以下几点:

  1. ROC 曲线能很容易的查出任意阈值对模型的泛化性能影响;
  2. 有助于选择最佳的阈值;
  3. 可以对不同的模型比较性能,在同一坐标中,靠近左上角的 ROC 曲所代表的学习器准确性最高。

1.6. 五、文本摘要

1.6.1. 1. 关键短语提取

关键短语提取通常是执行更复杂任务的起点。最终提取出来的是一个词汇集。

(1) 搭配

搭配是一种趋向频繁发生的序列或一组词。

可以使用原始频率、点互信息(pointwise mutual information, PMI)等度量方法来找到搭配。

(2) 基于权重标签的短语提取

步骤:

  1. 使用浅层分析提取所有的名词短语词块。
  2. 计算每个词块的TF-IDF权重,返回最大加权短语。

关键字提取

  • jieba.analyse.extract_tags:使用TF-IDF提取关键字
  • jieba.analyse.textrank:使用textRank算法提取关键字
  • 基于 LDA 主题模型进行关键词提取
    • 步骤为:文件加载 -> jieba 分词 -> 去停用词 -> 构建词袋模型 -> LDA 模型训练 -> 结果可视化。
from pyhanlp import HanLP
# 提取关键字
HanLP.extractKeyword(document, 2)

1.6.2. 2. 主题建模

1.6.3. 3. 自动文档摘要

from pyhanlp import HanLP
# 自动摘要
HanLP.extractSummary(document, 3)

1.7. 六、文本相似度

1.7.1. 1. 词项相似度分析

  • 汉明距离
  • 曼哈顿距离
  • 欧几里得距离
  • 莱文斯坦编辑距离
  • 余弦距离

1.7.2. 2. 文档相似度分析

  • 余弦相似度
  • 海灵格-巴塔恰亚距离
  • Okapi BM25排名

1.8. 七、文本分类/聚类

1.8.1. 1. 文本分类

文本分类是指利用计算机按照一定的分类标准或体系自动将文本分门别类,它不仅是自然语言处理问题,也是一个模式识别问题。

文本分类的核心内容:

  • 文本表示:向量空间模型VSM(如词袋模型、tf-idf模型)、统计模型(基本思路是挖掘文本的主题信息)。主题模型是当前文本表示研究的主要范式,LDA 模型是其典型代表
  • 分类模型:KNN、SVM、AdaBoost

文本分类一般包括文本预处理、分词、模型构建和分类几个过程。

文本分类一般分为5步:

文本 -> 预处理 -> 分词(未登录词识别) -> 特征提取/特征选择 -> 文本表示 -> 文本分类 -> 结果

  1. 文本预处理:去掉文本中多余的部分,如标点、介词等。
  2. 分词:对预处理后的文本进行词切分操作,并识别其中的未登录词。
  3. 特征提取和特征选择:得到文本分词结果后,选择文本特征提取方法,并对特征进行选择,约简特征,尽量降低维度,减少后续计算量。
  4. 文本表示:选择合适的方法表示选择的特征,作为分类的依据。
  5. 文本分类:选择合理的分类方法对文本进行分类,得到文本类别。

在文本分类中,分词方法特征选择以及分类算法是关键,主要也是对这几方面进行改进。

文本分类的一般方法:

  • 基于知识工程(KE,knowledge engineering)的分类方法
  • 基于机器学习(ML,machine learning)的分类方法。朴素贝叶斯、SVM、神经网络、决策树。

1.8.2. 2. 文本聚类

应用无监督的ML概念和技术,将文档分成不同的类别。

类之间总会有一些重叠,并没有一个完美聚类的定义。

文本聚类是将一个个文档由原有的自然语言文字信息转化成数学信息,以高维空间点的形式展现出来,通过计算哪些点距离比较近,从而将那些点聚成一个簇,簇的中心叫做簇心。

一个好的聚类要保证簇内点的距离尽量的近,但簇与簇之间的点要尽量的远。

  • k-means聚类
  • 近邻传播聚类
  • 沃德凝聚层次聚类

1.9. 八、情感分析

1.10. 九、可视化

在文本领域用的比较多的可视化类型有:

  • 基于文本内容的可视化:包括基于词频的可视化,基于词汇分布的可视化。常用的有词云、分布图和 Document Cards 等。

  • 基于文本关系的可视化:研究文本内外关系,帮助人们理解文本内容和发现规律。常用的可视化形式有树状图、节点连接的网络图、力导向图、叠式图和 Word Tree 等。

  • 基于多层面信息的可视化:研究如何结合信息的多个方面帮助用户从更深层次理解文本数据,发现其内在规律。其中,包含时间信息和地理坐标的文本可视化近年来受到越来越多的关注。常用的有地理热力图、ThemeRiver、SparkClouds、TextFlow 和基于矩阵视图的情感分析可视化等。

前端可视化学习网站:

  • 百度的 Echarts,基于 Canvas,适合刚入门的新手,遵循了数据可视化的一些经典范式,只要把数据组织好,就可以轻松得到很漂亮的图表。

  • D3.js,基于 SVG 方便自己定制,D3 V4 支持 Canvas+SVG,D3.js 比 Echarts 稍微难点,适合有一定开发经验的人。

  • three.js,是一个基于 WebGL 的 3D 图形的框架,可以让用户通过 JavaScript 搭建 WebGL 项目。

import networkx as nx
import matplotlib.pyplot as plt

# 设置matplotlib正常显示中文,用黑体显示中文
plt.rcParams['font.sans-serif']=['SimHei']  
plt.rcParams['axes.unicode_minus']=False 
colors = ['red', 'green', 'blue', 'yellow']

#有向图
DG = nx.DiGraph()

DG.add_node('A')
DG.add_node('B')
#添加边,有方向,A-->B
DG.add_edge('A','B')

#一次性添加多节点,输入的格式为列表
DG.add_nodes_from(['甘肃', '武威', '兰州', '张掖','凉州区'])
#添加边,数据格式为列表
DG.add_edges_from([('甘肃', '武威'), ('甘肃', '兰州'), ('甘肃','张掖'),('武威','凉州区')])
#作图,设置节点名显示,节点大小,节点颜色
nx.draw(DG,with_labels=True, node_size=900, node_color = colors)
plt.show()
Copyright @appwhy all right reserved,powered by Gitbook文件更新于: 2020-06-17 09:37:25

results matching ""

    No results matching ""