此文为学习何晗老师《自然语言处理入门》笔记
信息抽取
- 信息抽取:从非结构化文本中提取结构化信息的一类技术
- 基于规则的正则匹配
- 有监督机器学习
- 无监督机器学习
信息熵(entropy)
- 某条消息包含的信息量
互信息(Mutual Information)
- 指两个离散型随机变量与的相关程度的度量。
具体到新词提取应用中:
- :代表字符串的一个子串(前缀)
- :代表母串去掉该前缀剩下的部分(后缀)
新词提取
有了左右信息熵和互信息之后,将两个指标低于一定阈值的片段过滤,剩下的片段按频次降序排列,截取最高频次的个片段即完成了词语提取流程。
关键词提取
词频统计
流程:
- 分词
- 停用词过滤
- 按词频提取前个
其中,求个元素中前大()元素的问题通常通过最大堆解决,其复杂度为
TF-IDF
TF-IDF(Term Frequency-Inverse Document Frequency, 词频-倒排文档频次)
其中
- :单词(term)
- :文档(document)
- :代表在中出现频次
- :代表有多少篇文章包含
- :的倒数
TextRank
- TextRank:PageRank在文本上的应用
- PageRank:一种用于排序网页的随机算法。它的工作原理是将互联网看作是有向图,互联网上的网页视作节点,节点到节点的超链接视作有向边。初始化每个节点的权重都是1,以迭代的方式更新每个节点的权重:
?S(V_i) = (1 - d) + d \times \sum_{V_j \in In(V_i)} \frac {1} {|Out(V_j)|} S(V_j)?
- :介于(0, 1)之间的常数因子,在PageRank中模拟用户点击链接从而跳出当前网站的概率
- :表示链接到的节点集合
- :表示从出发链接到的节点集合
有公式可以看出,外链接权重跟外链接总数成反比,与提供外链接的网站权重成正比。
PageRank应用到关键词提取:
- 是将单词视作节点
- 每个单词的外链接来自自身前后固定大小的窗口内的所有单词
for (int i = 0; i < max_iter; i++) {
Map<String, Float> m = new HashMap<>();
float max_diff = 0;
// words存储着单词到邻居的映射
for (Map.Entry<String, Set<String> entry : words.entrySet()) {
String key = entry.getKey();
Set<String> value = entry.getValue();
m.put(key, 1 - d);
// 对应上面求和公式
for (String element : value) {
int size = words.get(element).size();
if (key.equals(element) || size == 0) continue;
m.put(key, m.get(key) + d / size * (score.get(element) == null ? 0 : score.get(element)));
}
max_diff = Math.max(max_diff, Math.abs(m.get(key) - (score.get(key) == null ? 0 : score.get(key))));
}
score = m;
if (max_diff <= min_diff) break;
}
短语提取
短语提取经常用于搜索引擎的自动推荐,文档的简介生成等。
利用互信息和左右信息熵,只需将新词提取时的字符替换为单词,字符串替换为单词列表即可。
关键句提取
为了将PageRank利用到句子颗粒度上去,引入了BM25算法衡量句子的相似度,改进链接的权重。这样的窗口的中心句子与相邻的句子间的链接变的有强有弱,相似的句子将得到更高的投票。
BM25
在信息检索领域,BM25是TF-IDF的一种改进变种。
- TF-IDF:衡量单个词语在文档中的重要程度
- BM25:衡量多个词语与文档的关联程度
- :查询语句
- :中关键字
- :为一个被检索的文档
- :常数,与可视做的权重参数,越大,对文档得分的正面影响越大,越大,文档长度对得分的负面影响越大。当时,完全等价于所有单词的之和。
- :所有文档平均长度
/**
* 计算一个句子与一个文档的BM25相似度
* @param sentence 句子(查询语句)
* @param index 文档(用语料库中的下标表示)
*/
double sim(List<String> sentence, int index) {
double score = 0;
for (String word : sentence) {
if (! f[index].containsKey(word)) {
continue;
}
int d = docs.get(index).get(word);
int tf = f[index].get(word);
score += (idf.get(word) * tf * (k + 1) / (tf + k * (1 - b + b * d / avgdl)));
}
return score;
}
TextRank
将一个句子视作查询语句,相邻的句子视作待查询的文档,就能得到他们之间的相似度。以此相似度作为PageRank中的链接的权重,于是得到一种改进算法TextRank:
- :文档中第个句子的得分,重复迭代若干次即可得到最终分值
for (int iter = 0; iter < max_iter; ++iter) {
double[] m = new double[D];
double max_diff = 0;
for (int i = 0; i < D; ++i) {
m[i] = 1 - d;
for (int j = 0; j < D; ++j) {
if (j == i || weight_sum[j] == 0) {
continue;
}
m[i] += (d * weight[j][i] / weight_sum[j] * vertex[j]);
}
double diff = Math.abs(m[i] = vertex[i]);
if (diff > max_diff) {
max_diff = diff;
}
}
vertex = m;
if (max_dff <= min_diff) {
break;
}
}
总结
新词提取与短语提取,关键词与关键句的提取,在原理上都是同一种算法在不同文本颗粒度上的应用。这些算法都无需标注语料参与,属于无监督学习。
文本聚类
聚类(cluster analysis)指的是将给定对象的集合划分为不同子集的过程。
- 硬聚类(hard clustering):每个元素被确定地归入一个簇
- 软聚类(soft clustering):每个元素与每个簇都存在一定的从属程度(隶属度),只不过该程度有大有小
根据聚类结果的结构,分为:
-
划分式(partitional):一些列不想交的子集
-
层次化(hierarchial):一棵树,叶子节点是元素,父节点是簇
-
文本聚类(text clustering):指的是对文档进行的聚类分析。广泛应用于文本挖掘和信息检索领域。
文本聚类基本流程:
- 特征提取
- 向量聚类
文档的特征提取
词袋模型
- 词袋(bag-of-words):信息检索与自然语言处理中最常用的文档表示模型,它将文档想象为一个装有词语的袋子,通过袋子中每种词语的计数等统计量将文档表示为向量。
定义由个文档组成的集合,定义其中第个文档的特征向量:
- :词表中第种单词,为词表大小
- :表示单词在稳定中出现次数。 做归一化处理
从文本到向量的转换已经执行完毕。
均值算法
给定个向量,以及一个整数,要求找出个簇,以及各自的质心,使得下式值最小:
- :向量与质心的欧拉距离
- :聚类的准则函数(criterion function).
质心的计算就是簇内数据点的几何平均:
其中,是簇内所有向量之和,成作合成向量(compose vector)。
生成个簇的均值迭代算法:
- 选取个点作为个簇的初始质心
- 将所有点分布分配给最近的质心所在的簇
- 重新计算每个簇的质心
- 重复2到3,直至之心不在发生变化
均值算法无法保证收敛到全局最优,但能够保证有效地收敛到一个局部最优点。
初始质心的选取
将之心的选取也视作准则函数进行迭代优化:
- 随机选取一个数据点作为质心,视作只有一个簇计算准则函数。同时维护每个点到最近质心的距离的平方,作为一个映射数组
- 随机取准则函数值的一部分
- 遍历剩下的所有数据点,若改点到质心的距离的平方小于,则选取该点添加到质心列表,同时更新准则函数与
- 循环2到3,直至凑足个初始质心
/**
* 选取初始质心
* @param ndocs 质心数量
* @param docs 输出到该列表中
*/
void choose_smartly(int ndocs, List<Document> docs) {
double po
}
文本分类
- 文本分类(text classification):又称文档分类,是将一个归类到一个或多个类别中的自然语言处理任务。是一个典型的监督学习任务,其流程离不开人工指导:人工标注文档类别。
应用:
- 垃圾邮件过滤
- 垃圾评论过滤
- 自动标签
- 情感分析
依存句法分析
短语结构树
上下文无关法(Context-Free Grammer, CFG)
- 终结符(teminal symbol,无法再分的最小单位)集合,比如汉语的一个词表
- 非终结符(nontermial symbol)集合,比如“名词短语”“动词短语”等短语结构组成的集合。 中至少包含一个特殊的非终结符,即句子符或初始符,记作
- 推导规则,即推导非终结符的一系列规则:
语法树其实与编译原理相应概念相同,但在NLP中,我们称其为短语结构树。
短语结构树
短语结构语法描述了如何自顶而下地生成一个句子。反过来,句子也可以用短语结构语法来递归地分解。
树库(treebank):语言学家制定短语结构语法规范,将大量句子人工分解为树形结构,形成一种语料库
依存句法树
不同于短语结构树,依存句法树并不关注如何生成句子这种宏大的命题。依存句法树关注的是句子中词语之间的语法联系,并将其约束为树形结构。
依存语法理论:词与词之间存在主从关系,这是一种二元不等价的关系。
- 从属词(dependent):如果一个词修饰领一个词
- 支配词(head):被修饰的词语
- 依存关系(dependency relation):两者之间的语法关系
依存语法树4个约束性公理
- 有且只有一个词语(ROOT,虚拟根节点,简称虚根)不依存于其他词语
- 除此之外所有单词必须依存于其他单词
- 每个单词不能依存于多个单词
- 如果单词依存于,那么位置处于和之间的单词只能依存于、或之间的单词
依存句法分析
依存句法分析(dependency parsing)指的是分析句子的依存语法的一种高级NLP任务,其输入通常是词语和词性,输出则是一颗依存句法树。
- 基于图的依存句法分析:依存语法树其实是完全图(complete graph,每个顶点都相连的图)的一个子图。
- 基于转移的依存句法分析
深度学习与自然语言处理
传统方法的局限
数据稀疏
- 传统机器学习方法不善于处理数据稀疏问题
- 语言是离散的符号系统,每个字符,每个单词都是离散型随机变量
- 任何机器学习模型只接受向量
- One-Hot模型会导致稀疏矩阵问题
词向量:将离散单词表示为稠密向量
特征模板
传统自然语言处理依赖于手工指定的特征模板,这些特征模板通常是小颗粒度文本单元的组合,用以模拟语言的符合过程
误差传播
深度学习与优势
- 用稠密向量解决数据稀疏
- 用多层网络自动提取特征表示
- 端到端的设计
Word2Vec
CBOW(Continuous Bag of Words Model)是一种基于窗口的语言模型。一个窗口指的是句子中的一个固定长度的片段,窗口中间的词语称为中心词。窗口中其他词语称为中心词的上下文。CBOW模型通过三层神经网络接受上下文的特征向量,预测中心词是什么。