第5章
CHAPTER 5


依存句法分析








句法分析的基本任务是确定句子的句法结构或者句子中词汇之间的依存关系。主要包括两方面
内容: 一是确定语言的语法体系,即对语言中合法句子的语法结构给予形式化的定义; 另一方面是句法分析技术,即根据给定的语法体系,自动推导出句子的句法结构,分析句子所包含的句法单位和这些句法单位之间的关系。

5.1依存句法分析原理[12]

句法分析是自然语言处理领域的一个关键问题,如能将其有效解决,一方面可对相应树库构建体系的正确性和完善性进行验证; 另一方面也可直接服务于各种上层应用,比如搜索引擎用户日志分析和关键词识别、信息提取、自动问答、机器翻译等其他自然语言处理相关的任务。



图5.1依存句法树(图片

来源于搜狐)


依存句法是由法国语言学家L.Tesniere最先提出,它将句子分析成一棵依存句法树,描述出各个词语之间的依存关系。依存句法指出了词语之间在句法上的搭配关系,这种搭配关系是和语义相关联的。例如,句子“会议宣布了首批资深院士名单。”的依存句法树如图5.1所示。


从图5.1可以看出,词“宣布”支配“会议”“了”“名单”,故可以将这些支配词作为“宣布”的搭配词。

1. 句法分析是什么

句法分析(syntactic parsing)是自然语言处理中的关键技术之一,它是对输入的文本句子进行分析以得到句子的句法结构的处理过程。对句法结构进行分析,一方面是语言理解的自身需求,句法分析是语言理解的重要一环; 另一方面也为其他自然语言处理任务提供支持。例如,句法驱动的统计机器翻译需要对源语言或目标语言(或者同时两种语言)进行句法分析。


语义分析通常以句法分析的输出结果作为输入以便获得更多的指示信息。根据句法结构的表示形式不同,最常见的句法分析任务可以分为以下3种: 

(1) 句法结构分析(syntactic structure parsing),又称短语结构分析(phrase structure parsing),也叫成分句法分析(constituent syntactic parsing)。作用是识别出句子中的短语结构以及短语之间的层次句法关系。

(2) 依存关系分析,又称依存句法分析(dependency syntactic parsing),简称依存分析,作用是识别句子中词汇与词汇之间的相互依存关系。

(3) 深层文法句法分析,即利用深层文法,例如,词汇化树邻接文法(lexicalized tree adjoining grammar,LTAG)、词汇功能文法(lexical functional grammar,LFG)、组合范畴文法(combinatory categorial grammar,CCG)等,对句子进行深层的句法以及语义分析。



在自然语言处理中,用词与词之间的依存关系来描述语言结构的框架称为依存句法(dependence grammar),又称从属关系语法。利用依存句法进行句法分析是自然语言理解的重要技术之一。

2. 重要概念


依存句法认为“谓语”中的动词是一个句子的中心,其他成分与动词直接或间接地产生联系。在依存句法理论中,“依存”指词与词之间支配与被支配的关系,这种关系不是对等的,这种关系具有方向。确切地说,处于支配地位的成分称之为支配者(governor、regent、head),而处于被支配地位的成分称之为从属者(modifier、subordinate、dependency)。

依存句法本身没有规定要对依存关系进行分类,但为了丰富依存结构传达的句法信息,在实际应用中,一般会给依存树的边加上不同的标记。依存句法存在一个共同的基本假设: 句法结构本质上包含词和词之间的依存(修饰)关系。一个依存关系连接两个词,分别是核心词(head)和依存词(dependent)。依存关系可以细分为不同的类型,表示两个词之间的具体句法关系。


3. 常见方法

(1) 基于规则的方法。 早期基于依存句法的句法分析方法主要包括类似CYK的动态规划算法、基于约束满足的方法和确定性分析策略等。

(2) 基于统计的方法。统计自然语言处理领域也涌现出了一大批优秀的研究成果,包括生成式依存分析方法、判别式依存分析方法和确定性依存分析方法,这几类方法是数据驱动的统计依存分析中最具代表性的方法。


(3) 基于深度学习的方法。近年来,深度学习在句法分析课题上逐渐成为研究热点,主要研究工作集中在特征表示方面。传统的特征表示方法主要采用人工定义原子特征和特征组合,而深度学习则把原子特征(词、词性、类别标签)进行向量化,再利用多层神经元网络提取特征。


通常使用的指标包括无标记依存正确率(unlabeled attachment score,UAS)、带标记依存正确率(labeled attachment score,LAS)、依存正确率(dependency accuracy,DA)、根正确率(root accuracy,RA)、完全匹配率(complete match,CM)等。这些指标的具体意思如下: 

(1) 无标记依存正确率(UAS)——测试集中找到其正确支配词的词(包括没有标注支配词的根节点)所占总词数的百分比。

(2) 带标记依存正确率(LAS)——测试集中找到其正确支配词的词,并且依存关系类型也标注正确的词(包括没有标注支配词的
根节点)占总词数的百分比。

(3) 依存正确率(DA)——测试集中找到正确支配词非根节点词占所有非根节点词总数的百分比。

(4) 根正确率(RA)——有两种定义: 一种是测试集中正确根节点的个数与句子个数的百分比; 另一种是指测试集中找到正确根节点的句子数所占句子总数的百分比。

(5) 完全匹配率(CM)——测试集中无标记依存结构完全正确的句子占句子总数的百分比。

4. 数据集

Penn Treebank是一个项目的名称,该项目的目的是对语料进行标注,标注内容包括词性标注以及句法分析。

CoNLL经常开放句法分析的学术评测。

5. 相关开源工具介绍

下面介绍几个相关开源工具。

1) StanfordCoreNLP

该工具由
斯坦福大学开发,提供依存句法分析功能。

Github地址: https://github.com/Lynten/stanfordcorenlp。

官网: https://stanfordnlp.github.io/CoreNLP/。

安装: pip install stanfordcorenlp。

国内源安装: pip install stanfordcorenlp i https://pypi.tuna.tsinghua.edu.cn/simple。

使用StanfordCoreNLP进行依存句法分析:


先下载模型,下载地址: https://nlp.stanford.edu/software/corenlpbackupdownload.html。

再使用例子进行依存句法分析,代码如下: 

from stanfordcorenlp import StanfordCoreNLP

# 对中文进行依存句法分析

zh_model = StanfordCoreNLP(r'stanford-corenlp-full-2018-02-27', lang= 'zh')

s_zh = '我爱自然语言处理技术!'

dep_zh = zh_model.dependency_parse(s_zh)

print(dep_zh)

[('ROOT', 0, 4), ('nsubj', 4, 1), ('advmod', 4, 2), ('nsubj', 4, 3), ('dobj', 4, 5), ('punct', 4, 6)]

# 对英文进行依存句法分析

eng_model = StanfordCoreNLP( r'stanford-corenlp-full-2018-02-27')

s_eng = 'I love natural language processing technology!'

dep_eng = eng_model.dependency_parse(s_eng)

print(dep_eng)

[('ROOT', 0, 2), ('nsubj', 2, 1), ('amod', 6, 3), ('compound', 6, 4), ('compound', 6, 5), ('dobj', 2, 6), ('punct', 2, 7)]

2) HanLP

HanLP是一系列模型与算法组成的自然语言处理工具包,它提供了中文依存句法分析功能。

Github地址: https://github.com/hankcs/pyhanlp。

官网: http://hanlp.linrunsoft.com/。

安装: pip install pyhanlp。

国内源安装: pip install pyhanlp i https://pypi.tuna.tsinghua.edu.cn/simple。

使用该工具对示例进行依存句法分析的代码如下: 

from pyhanlp import *

s_zh = '我爱自然语言处理技术!'

dep_zh = HanLP.parseDependency(s_zh)

print(dep_zh)

1我 我 r r _ 2主谓关系 _ _

2爱 爱 v v _ 0核心关系 _ _

3自然语言处理 自然语言处理 v v _ 4定中关系 _ _

4技术 技术 n n _ 2动宾关系 _ _

5! ! wp w _ 2标点符号 _ _: 

3) SpaCy

该工具为工业级的自然语言处理工具,遗憾的是目前不支持中文。

4) FudanNLP

该工具为
复旦大学自然语言处理实验室开发的中文自然语言处理工具包,包含信息检索
(文本分类、新闻聚类)、中文处理(中文分词、词性标注、实体名识别、关键词提取、依存句法分析、时间短语识别
)、结构化学习(在线学习、层次分类、聚类)。

5.2HanLP基于神经网络依存句法分析器[13]

HanLP本身提供了基于神经网络的依存句法分析器,除此之外,还提供了很多句法分析器,其结构如图5.2所示。



图5.2句法分析器接口(图片来源于CSDN)


句法分析器接口代码如下所示: 

/**

* 依存句法分析器接口

*

* @author hankcs

*/

public interface IDependencyParser

{

/**

* 分析句子的依存句法

*

* @param termList 句子,可以是任何具有词性标注功能的分词器的分词结果

* @return CoNLL格式的依存句法树

*/

CoNLLSentence parse(List<Term> termList);



/**

* 分析句子的依存句法

*

* @param sentence 句子

* @return CoNLL格式的依存句法树

*/

CoNLLSentence parse(String sentence);



/**

* 获取Parser使用的分词器

*

* @return

*/

Segment getSegment();



/**

* 设置Parser使用的分词器

*

* @param segment

*/

IDependencyParser setSegment(Segment segment);



/**

* 获取依存关系映射表

*

* @return

*/

Map<String, String> getDeprelTranslator();



/**

* 设置依存关系映射表

*

* @param deprelTranslator

*/

IDependencyParser setDeprelTranslator(Map<String, String> deprelTranslator);



/**

* 依存关系自动转换开关

* @param enable

*/

IDependencyParser enableDeprelTranslator(boolean enable);

}

简单示例代码如下: 

/**

* 依存句法分析(神经网络句法模型需要-Xms1g -Xmx1g -Xmn512m)

* @author hankcs

*/

public class DemoDependencyParser

{

public static void main(String[] args)

{

CoNLLSentence sentence = HanLP.parseDependency("徐先生还具体帮助他确定了把画雄鹰、松鼠和麻雀作为主攻目标。");

System.out.println(sentence);

// 可以方便地遍历它

for (CoNLLWord word : sentence)

{

System.out.printf("%s --(%s)--> %s\n", word.LEMMA, word.DEPREL, word.HEAD.LEMMA);

}

// 也可以直接拿到数组,任意顺序或逆序遍历

CoNLLWord[] wordArray = sentence.getWordArray();

for (int i = wordArray.length - 1; i>= 0; i--)

{

CoNLLWord word = wordArray[i];

System.out.printf("%s --(%s)--> %s\n", word.LEMMA, word.DEPREL, word.HEAD.LEMMA);

}

// 还可以直接遍历子树,从某棵子树的某个节点一路遍历到虚根

CoNLLWord head = wordArray[12];

while ((head = head.HEAD) != null)

{

if (head == CoNLLWord.ROOT) System.out.println(head.LEMMA);

else System.out.printf("%s --(%s)--> ", head.LEMMA, head.DEPREL);

}

}

}

运行结果如下: 

1.1徐先生徐先生nhnr_4主谓关系__

2.2还还dd_4状中结构__

3.3具体具体aa_4状中结构__

4.4帮助帮助vv_0核心关系__

5.5他他 rrr_4兼语__

6.6确定确定vv_4动宾关系__

7.7了了uule_6右附加关系__

8.8把把ppba_15状中结构__

9.9画画vv_8介宾关系__

10.10雄鹰 雄鹰nn_9动宾关系__

11.11、、wpw_12标点符号__

12.12松鼠 松鼠nn_10并列关系__

13.13和和ccc_14左附加关系__

14.14麻雀 麻雀nn_10并列关系__

15.15作为 作为pp_6动宾关系__

16.16主攻 主攻vv_17定中关系__

17.17目标 目标nn_15动宾关系__

18.18。。wpw_4标点符号__

19.

20.徐先生 --(主谓关系)--> 帮助

21.还 --(状中结构)--> 帮助

22.具体 --(状中结构)--> 帮助

23.帮助 --(核心关系)--> ##核心##

24.他 --(兼语)--> 帮助

25.确定 --(动宾关系)--> 帮助

26.了 --(右附加关系)--> 确定

27.把 --(状中结构)--> 作为

28.画 --(介宾关系)--> 把

29.雄鹰 --(动宾关系)--> 画

30.、 --(标点符号)--> 松鼠

31.松鼠 --(并列关系)--> 雄鹰

32.和 --(左附加关系)--> 麻雀

33.麻雀 --(并列关系)--> 雄鹰

34.作为 --(动宾关系)--> 确定

35.主攻 --(定中关系)--> 目标

36.目标 --(动宾关系)--> 作为

37.。 --(标点符号)--> 帮助

38.

39.。 --(标点符号)--> 帮助

40.目标 --(动宾关系)--> 作为

41.主攻 --(定中关系)--> 目标

42.作为 --(动宾关系)--> 确定

43.麻雀 --(并列关系)--> 雄鹰

44.和 --(左附加关系)--> 麻雀

45.松鼠 --(并列关系)--> 雄鹰

46.、 --(标点符号)--> 松鼠

47.雄鹰 --(动宾关系)--> 画

48.画 --(介宾关系)--> 把

49.把 --(状中结构)--> 作为

50.了 --(右附加关系)--> 确定

51.确定 --(动宾关系)--> 帮助

52.他 --(兼语)--> 帮助

53.帮助 --(核心关系)--> ##核心##

54.具体 --(状中结构)--> 帮助

55.还 --(状中结构)--> 帮助

56.徐先生 --(主谓关系)--> 帮助

57.

58.麻雀 --(并列关系)--> 雄鹰 --(动宾关系)--> 画 --(介宾关系)--> 把 --(状中结构)--> 作为 --(动宾关系)--> 确定

各类关系解释如下: 

(1) 主谓关系(subjectverb,SBV): 我送她一束花 (我 < 送)。

(2) 动宾关系(verbobject,VOB): 我送她一束花 (送 > 花)。

(3) 间宾关系(indirectobject,IOB): 我送她一束花 (送 > 她)。

(4) 前置宾语(frontingobject,FOB): 他什么书都读 (书 < 读)。

(5) 兼语(double,DBL): 他请我吃饭 (请 > 我)。

(6) 定中关系(attribute,ATT): 红苹果 (红 < 苹果)。

(7) 状中结构(adverbial,ADV): 非常美丽 (非常 < 美丽)。

(8) 动补结构(complement,CMP): 做完了作业 (做 > 完)。

(9) 并列关系(coordinate,COO): 大山和大海 (大山 > 大海)。

(10) 介宾关系(prepositionobject,POB): 在贸易区内 (在 > 内)。

(11) 左附加关系(left adjunct,LAD): 大山和大海 (和 < 大海)。

(12) 右附加关系(right adjunct,RAD): 孩子们 (孩子 > 们)。

(13) 独立结构(independent structure,IS): 两个单句在结构上彼此独立。

(14) 核心关系(head,HED): 指整个句子的核心。

可以使用DependencyViewer进行可视化,如图5.3所示。



图5.3依存句法关系(图片来源于CSDN)













第6章
CHAPTER 6


语义角色标注








语义角色标注(semantic role labeling,SRL)是一种浅层的语义分析。对于给定的一个句子,SRL 的任务是找出句子中谓词的相应语义角色成分,包括核心语义角色(如施事者、受事者等) 和附属语义角色(如地点、时间、方式、原因等)。

SRL的研究热点包括基于成分句法树的SRL和基于依存句法树的
SRL。同时,根据谓词的词性不同,又可进一步分为动词性谓词和名词性谓词SRL。尽管各任务之间存在着差异性,但它们的标注框架类似。


目前SRL的实现通常都是基于句法分析结果,即对于某个给定的句子,首先得到其句法分析结果,然后基于该句法分析结果,再实现SRL。这使得SRL的性能严重依赖于句法分析的结果。

6.1语义角色标注原理


自然语言分析技术大致分为3个层面: 词法分析、句法分析和语义分析。
SRL是实现浅层语义分析的一种方式。在一个句子中,谓词是对主语的陈述或说明,指出“做什么”“是什么”或“怎么样”,代表了一个事件的核心,跟谓词搭配的名词称为论元(argument)。语义角色是指论元在动词所指事件中担任的角色,主要有
施事者(agent)、受事者(patient)、
时间(time)、经验者(experiencer)、受益者(beneficiary)、工具(instrument)、地点(location)、目标(goal)和来源(source)等。


如下例中,“遇到”是谓词(predicate,通常简写为Pred),“小明”是施事者,“小红”是受事者,“昨天”是事件发生的时间
,“公园”是事件发生的地点。


[小明]Agent[昨天]Time[晚上]Time在[公园]Location[遇到]Predicate了[小红]Patient。

SRL以句子的谓词为中心,不对句子所包含的语义信息进行深入分析,只分析句子中各成分与谓词之间的关系,即句子的谓词
论元结构,并用语义角色来描述这些结构关系,是许多自然语言理解任务(如信息提取
、篇章分析、深度问答等)的重要中间步骤。在研究中一般都假定谓词是给定的,所要做的就是找出给定谓词的各个论元和它们的语义角色。传统的SRL系统大多建立在句法分析基础之上,通常包括5个流程: 


(1) 构建一棵句法分析树,
上面的例子是进行依存句法分析得到的一棵句法树。

(2) 从句法树上识别出给定谓词的候选论元。

(3) 候选论元剪除。一个句子中的候选论元可能很多,候选论元剪除就是从大量的候选项中剪除那些最不可能成为论元的候选项。

(4) 论元识别。这个过程是从上一步剪除之后的候选项中判断哪些是真正的论元,通常当作一个二分类问题来解决。

(5) 针对第(4)步的结果,通过多分类得到论元的语义角色标签。

可以看到,句法分析是基础,并且后续步骤常常会构造一些人工特征,这些特征往往也来自句法分析。依存句法分析
树如图6.1所示。




图6.1依存句法分析树(图片来源于CSDN)



然而,完全句法分析需要确定句子所包含的全部句法信息,并确定句子各成分之间的关系,这是一个非常困难的任务。目前技术下的句法分析准确率并不高,句法分析的细微错误都会导致SRL的错误。为了降低问题的复杂度,同时获得一定的句法结构信息,“浅层句法分析”的思想应运而生。浅层句法分析也称为部分句法分析(partial parsing)或语块划分(chunking)。和完全句法分析得到一棵完整的句法树不同,浅层句法分析只需识别句子中某些结构相对简单的独立成分,例如,动词短语,这些被识别出来的结构称为语块(chunk)。为了回避“无法获得准确率较高的句法树”所带来的困难,一些研究也提出了基于语块的SRL方法。



基于语块的SRL方法将SRL作为一个序列标注问题来解决。序列标注任务一般都会采用BIO表示方式来定义序列标注的标签集
。在BIO表示法中,B代表语块的开始,I代表语块的中间,O代表语块结束。通过B、I、O 3种标记将不同的语块赋予不同的标签,例如,对于一个角色为A的论元,将它所包含的第一个语块赋予标签BA,将它所包含的其他语块赋予标签IA,不属于任何论元的语块赋予标签O。


继续以上面的这句话为例,BIO标注方法如图6.2所示。



图6.2BIO标注方法(图片来源于CSDN)



从上例可看到,根据序列标注结果可以直接得到论元的
SRL结果,这是一个相对简单的过程。这种简单性体现在: 


(1) 依赖浅层句法分析,降低了句法分析的要求和难度; 

(2) 没有了候选论元剪除这一步骤; 

(3) 论元的识别和论元标注是同时实现的。这种一体化处理论元识别和论元标注的方法,简化了流程,降低了错误累积的风险,往往能够取得更好的结果。

6.2语义角色标注的设计框架[15]

语义角色包括: 

ARG0、ARG1、ARG2、ARG3、ARG4

ARGMLOC(地点)、ARGMTMP(时间)、ARGMCND(条件)、ARGMPRD(修饰)、ARGMBNF(受益)、ARGMMNR(方式)、ARGMDIR(来自)、ARGMADV(其他的)、ARGMDIS、ARGMFRQ、ARGMEXT、ARGMTPC

REL(谓语动词)


数据集分为训练数据集、开发数据集和测试数据集。数据集格式为: 每行一个句子,每个句子都有且仅有一个命题标签
(rel),并且句子已经完成中文分词。对于每一个词块A/B/C,A是该词; B是词性信息; C是论元标记。论元标记信息在测试数据集中没有给出,在训练数据集和开发数据集中给出。

论元标记由两部分组成: 位置标签和标记内容。位置标签共有4种,分别是S(单词论元词)、B(论元的首词语),E(论元的尾词) 以及 I(论元首尾词之间的词)。


对于含有多个词的论元,需要正确识别出它的论元标签以及左右边界。比如: 

《/PU/BARG1 国家/NN/IARG1高新/JJ/IARG1 技术/NN/IARG1\产业/NN/IARG1 开发区/NN/IARG1管理/NN/IARG1 暂行/JJ/IARG1\办法/NN/IARG1》/PU/EARG1


在B标签和E标签之间的所有位置的标签都是I标签,在输出语义角色标注答案时也应该按照此项原则。


语义角色标注在语义生成树的基础之上进行。语义角色标注的设计框架一共对数据进行4个阶段的处理: 生成语义生成树、剪枝、角色识别、角色分类。

6.2.1生成语义生成树


生成句子对应的语义生成树,使用了Standford开源的parser工具,例如: 


他 同时 希望 小明 本人 顺应 历史 发展 潮流,把握 时机,就 两 个 事件 谈判 作出 积极 回应 和 明智 选择。

生成的语义生成树如图6.3所示。



图6.3语义生成树(图片来源于CSDN)



6.2.2剪枝


如果用朴素的思路去遍历所有的节点,从图6.3的生成树中可以看出,这样需要处理的节点个数非常多。而事实上其中的节点是有冗余的,并不需要处理所有的节点。于是,如何去掉那些明显不可能是语义角色的节点呢?答案便是剪枝,仅仅处理可能是语义角色的候选节点即可。

(1) 采用[Xue and Palmer (2004)] 提出的启发式剪枝方法。

(2) 将谓语动词作为当前节点,将当前节点的兄弟节点全部收录到候选节点中。


(3) 将当前节点的父节点作为当前节点,重复第(1)步,直至最顶层的节点结束。

6.2.3角色识别

利用一个二分类器将收录的候选节点进行分类,是语义角色的节点标注为1,否则标注为0。

6.2.4角色分类


利用角色识别的结果,对标注为语义角色的节点进行分类并标注,这里的分类就是前
文所述的ARG0~4、REL、ARGM*。


当然,到这里可能会有一个疑问: 为什么不把角色识别和角色分类合并到一起,添加非语义角色类不就好了吗?这个思路本身没有任何问题,但是实际情况是合并的效果并不好。可能的解释是: 
起初先判断是不是语义角色,区分出来后,可以对后续的角色更加高效地进行分类。


有了语义角色标注的设计框架之后,其中的角色识别和角色分类都需要为节点设计特征。

这里的标注使用了12个特征: 


(1) 谓语动词

(2) 谓语动词词性

(3) 主被动

(4) 位置(谓语动词前、后)

(5) 关键词

(6) 关键词词性

(7) 分析类型

(8) 上升路径

(9) 下降路径

(10) 动词的子结构(动词的父节点和该父节点的类型组成)

(11) 短语第一个词

(12) 短语最后一个词

其中,“路径”是指该节点在语义生成树中到谓语动词所在节点的最短路径。


分类器的选择使用了快速梯度下降法(SGD)、决策树(DT)、k近邻(KNN)、朴素贝叶斯、支持向量机
(SVM)、最大熵(ME)等,以及一些集成方法
——Bagging(BAG)和AdaBoost(AB)。先使用每个方法训练得到各自的二分类器和多分类器,
再将二分类器和多分类器组合,根据结果选择最好的两个组合。


实验中使用了sklearn包中10种机器学习的方法: SGD、DT、KNN、GNB(高斯)、SVM、BAG、RF
(随机森林)、AB、CD(KNN簇中心)、ME。在开发数据集上实验结果的F值如图6.4所示,
其中,纵向分类器用于二分类器,横向分类器用于多分类器。



图6.4二分类器和多分类器组合的F值(图片来源于CSDN)



图中每行中F值超过0.5的数值且最高的有3个
。实验结果显示,二分类器和多分类器均使用RF在cpbdev.txt的数据集上可以得到最高F值: 0.5940(召回率为0.7121,准确率为0.5094)。