自然语言处理任务中,有很重要的一块,就是分析语言的结构。语言的结构,一般可以有两种视角:
1. 组成关系(Constituency)
句法结构分析(syntactic structure parsing),又称短语结构分析(phrase structure parsing),也叫成分句法分析(constituent syntactic parsing)。作用是识别出句子中的短语结构以及短语之间的层次句法关系。
2. 依赖关系(Dependency)
依存关系分析,又称依存句法分析(dependency syntactic parsing),简称依存分析,作用是识别句子中词汇与词汇之间的相互依存关系。依存句法是由法国语言学家L.Tesniere最先提出。它将句子分析成一颗依存句法树,描述出各个词语之间的依存关系。也即指出了词语之间在句法上的搭配关系,这种搭配关系是和语义相关联的。在自然语言处理中,用词与词之间的依存关系来描述语言结构的框架称为依存语法(dependence grammar),又称从属关系语法。利用依存句法进行句法分析是自然语言理解的重要技术之一。
虽然 20 世纪 90 年代大部分句法分析的研究工作都集中在短语结构树,但是由于短语结构语法比较复杂,相应句法分析器的准确率并不高。目前的句法分析已经从句法结构分析转向依存句法分析。
在过去10年间,在自然语言处理中,依存分析实质上已经取代结构分析。人们发现依存关系语法仅仅是构建语义表征来轻松得到语言理解的一种合适的框架,它们允许构建非常快而有效的解析。1990年代的论文基本就是关于短语结构文法,但现如今80%的论文在使用句法表示时使用了依存关系表示。
1️⃣ 一个依存关系连接两个词,分别是 核心词(或称支配词,head)和 依存词(或称从属词,dependent)。依存关系可以细分为不同的类型,表示两个词之间的具体句法关系。箭头从head起始,指向dependent。将一个句子中所有词语的依存关系以有向边的形式表示出来,就会得到一棵树,称为依存句法树。
2️⃣ 在20世纪70年代,Robinson提出依存语法中关于依存关系的四条公理(它们分别约束了依存句法树的根节点唯一性、连通、无环和投射性 ( projective)
1. 一个句子中只有一个词语是独立的; 根节点唯一性
2. 其它词语直接依存于某一词语; 连通性
3. 任何一个词语都不能依存与两个或两个以上的词语; 无环性
4. 如果单词A直接依存于单词B,而单词C在句中位于A和B之间,那么C或者直接依存于B,或者直接依存于A和B之间的某一成分; 投射性
90年代,中国学者开始将依赖语法引入汉语语言学,并结合汉语语法提出了第五个依赖关系公理:5. 中心成分左右两面的其它成分相互不发生关系。
3️⃣ 标签表示从属的语法功能,常用的依赖标签集 Universal Dependency Relations
- root:中心词,通常是动词
- nsubj:名词性主语(nominal subject)
- dobj:直接宾语(direct object)
- prep:介词
- pobj:介词宾语
- cc:连词
- compound:复合词
- advmod:状语
- det:限定词
- amod:形容词修饰语
1)基于规则的方法:早期的基于依存语法的句法分析方法主要包括类似CYK的动态规划算法、基于约束满足的方法和确定性分析策略等。
2)基于统计的方法:一种是基于图的方法(Graph Based),一种是基于转移(Transition Based)的方法。
现在的主流是基于统计的方法 [来源]
基于图的依存句法分析通常需要使用一个特征提取器为每个单词提取特征,然后将每两个单词的特征向量交给分类器打分,作为它们之间存在依存关系的分数。在传统机器学习时代,基于图的依存句法分析器往往面临运行开销大的问题。这是由于传统机器学习所依赖的特征过于稀疏,训练算法需要在整个图上进行全局的结构化预测等。考虑到这些问题,另一种基于转移的路线在传统机器学习框架下显得更加实用。[摘自《自然语言处理入门》]
该部分直接引用 SimpleAI 作者郭必扬:自然语言中的依存分析(Dependency Parsing)
Nivre在2003年提出的“Greedy Deterministic Transition-Based Parsing”方法,一度成为依存分析的标准方法。
我们构造一个三元组,分别是Stack、Buffer和一个Dependency Set。
Stack最开始只存放一个Root节点;
Buffer则装有我们需要解析的一个句子;
Set中则保存我们分析出来的依赖关系,最开始是空的。
我们要做的事情,就是不断地把Buffer中的词往Stack中推,跟Stack中的词判断是否有依赖关系,有的话则输出到Set中,直到Buffer中的词全部推出,Stack中也仅剩一个Root,就分析完毕了。
通过一个十分简单的例子,来演示这个过程。
分析的过程如下:
上面的过程怎么理解呢?比方从第二行,这个时候Stack中只有[Root,I],不构成依赖关系,所以我们需要从Buffer中“进货”了,因此采取的Action是Shift(把Buffer中的首个词,移动到Stack中),于是就到了第三行。
第三行,我们的Stack变成了[Root,I,love],其中I和Love构成了依赖关系,且是Love指向I,即“向左指”的依赖关系,因此我们将采取“Left Arc”的action,把被依赖的词(此时就是关系中的左边的词)给移除Stack,把这个关系给放入到Dependency Set中。
按照这样的方法,我们一直进行,不断地根据Stack和Buffer的情况,来从Shift、Left-arc、Right-arc三种动作中选择我们下一步应该怎么做,知道Stack中只剩一个Root,Buffer也空了,这个时候,分析就结束,我们就得到了最终的Dependency Set。
- 基于转移的依存分析有哪些Action?
① 移进(shift)② 左规约(arc_left) ③ 右规约(arc_right)④ 根出栈(reduce):根节点出栈,分析完毕。
- 怎么让机器去决定当前的Action呢?即机器怎么知道,Stack中是否构成了依赖关系?
在Nivre的年代,这里使用是机器学习的方法,需要做繁重的特征工程。这里的特征,往往有~个二值特征,即无数个指示条件作为特征,来训练模型,可以想象这么高纬度的特征是十分稀疏的。因此,这种模型的95%左右的解析时间,都花费在计算特征上。这也是传统方法的主要问题。
神经依存分析方法,是斯坦福团队2014年的研究成果,主要就是利用了神经网络的方法代替了传统机器学习方法、用低维分布式表示来代替传统方法的复杂的高维稀疏特征表示。而整个解析的过程,依然是根据之前的Transition-based方法。在神经依存分析中,我们的特征是怎么构建的呢?我们可以利用的信息包括词(word)、词性(pos tag)和依赖关系的标签(label)。我们对这三者,都进行低维分布式表示,即通过Embedding的方法,把离散的word、label、tag都转化成低维向量表示。
对基于转移的依存句法分析器而言,它学习和预测的对象是一系列转移动作。然而依存句法树库是一棵树,并不是现成的转移动作序列。这时候就需要一个算法将语料库中的依存句法树转换为正确的转移动作序列,以供机器学习模块学习。
最简单的转换算法直接人工编写一些规则为每棵树生成一个规范,这类算法称为静态规范 ( static oracle )。由于一棵树对应的拼装动作序列并非只有一种,静态规范也并不能保证得出最简单、最容易学习的那一种,所以存在着许多局限性。相反,另一类算法并不显式地输出唯一规范,而是让机器学习模型自由试错,一且无法拼装出正确语法树,则惩罚模型,这类算法称为动态规范 (dynamic oracle)。机器学习模型每执行一个动作,系统的状态就会转移到一个新状态中。动态规范算法计算新状态是否可以通过若干动作达到输出正确句法树的状态,若无法抵达,则惩罚模型。一般说来,动态规范的试验准确率要比静态规范高出几个百分点。
成分句法分析是分析两个相邻的token能否构成constituent;而依存句法分析是分析任意两个词汇的关系。
依存句法分析的输入是任意两个词汇,训练目标是判断这两个词汇间是否有关系,即左侧的词汇应不应该指到右侧的词汇,二分类任务。如果有关系,再判断是什么关系,多分类任务 [来源]
https://blog.csdn.net/weixin_41510260/article/details/104381546
句法分析也可以使用深度学习技术来学习,本质上也是一个Seq2Seq的问题。
树形结构可以对应生成这样一个序列:
两个集合A(标准答案,来自测试集)和 (预测结果)。
相较 LAS,UAS仅仅衡量支配词(head)的预测准确率,不衡量依存关系的准确率,一般分数更高。
无法从依存树还原出一个句子,树没有句子顺序
如果一个依存树中没有交叉的弧,那它就是投射性的 [来源] 基于转换的方法只能产生投射树,因此任何具有非投射结构的句子都必然包含一些错误。这种限制是使用更灵活的基于图的解析方法的动机之一。
使用最广泛的英语依赖树库是通过使用head-finding规则自动从短语结构树库中派生出来的。以这种方式生成的树保证是投射的,因为它们是由上下文无关的语法生成的。
中文依存句法树库目前最有名的开源自由的依存树库当属UD ( Universal Dependencies),它以“署名-非商业性使用-相同方式共享4.0”等类似协议免费向公众授权。UD是个跨语种的语法标注项目,一共有 200 多名贡献者为 70 多种语言标注了 100 多个树库。具体到中文,存在4个不同领域的树库。其中规模最大的为 UD_ Chinese GSD,该树库的语种为繁体中文(何晗将其转换为简体中文,详见 http://file.hankcs.com/corpus/chs-gsd-ud.zip
另一份著名的语料库依然是 CTB,只不过需要额外利用一些工具将短语结构树转换为依存句法树。读者可以直接下载转换后的 CTB 依存句法树库,其格式是类似于 CoNLL-U 的 CoNLL。 详见 http://file.hankcs.com/corpus/ctb8.0-dep.zip
StanfordCoreNLP:斯坦福大学开发的,提供依存句法分析功能。https://corenlp.run/
HanLP:HanLP是一系列模型与算法组成的NLP工具包。提供了中文依存句法分析功能。https://hanlp.hankcs.com/
SpaCy:工业级的自然语言处理工具,也支持中文的依存分析 https://explosion.ai/demos/displacy
FudanNLP:复旦大学自然语言处理实验室开发的中文自然语言处理工具包
LTP:哈工大 http://ltp.ai/demo.html
依存工具学习系列:
- 哈工大LTP的依存分析
- 百度DDParser的依存分析
Spacy的依存分析
HanLP的依存分析
依存分析,并不是我们NLP中最常见的任务之一,我们也很少看到直接将依存分析做应用的,我们更常见的是分类、实体识别、阅读理解、对话等任务。但是依存分析,作为自然语言处理的一项基础技术,试图让机器去理解语言的内部结构,理解了结构,NLU(Natural Language Understanding)才成为可能。
何晗(HanLP开发者):我粗略地将NLP 任务分为工具性(词法分析、句法分析等)和应用性(文本分类、 机器翻译等)两种,其中应用性 NLP 任务通常需要综合多个工具性 NLP 任务才能进行。
在知乎的一个问题讨论,可以看看:句法分析 (syntactic parsing) 在 NLP 领域的应用是怎样的?
⭐CS224n笔记[4]:自然语言中的依存分析
一文读懂依存句法分析-搜狐
详解依存句法分析
依存句法分析-知乎
依存句法分析小结
cs224n | 依存关系
依存句法分析_Dan Jurafsky《自然语言处理综述》(第三版)
依存句法分析的可视化及图分析