想象你把一盒乐高倒在地上:有 12 块红色方砖、8 块蓝色长条、几扇窗户和一个小人。如果只看清单,你只知道有哪些零件,却不知道下一步该把它们拼成什么。对机器来说,读一个句子也是这个道理。分词能告诉它句子里有“我”“爱”“自然语言处理”这些词,但“谁爱谁”“爱什么”这种拼接关系,只有句法分析能讲清楚。 句法分析(Parsing)要做的事,就是让机器像对照乐高说明书一样,把线性的一串词重组成一棵有层次的“语法树”。站在城堡旁,你可以用两种视角观察:一种看“承重关系”——哪块积木托着哪块,这叫依存句法;另一种看“模块嵌套”——城堡先分成塔楼、城墙,再层层拆成小零件,这叫成分句法。现代的 spaCy、stanza 等工具,就像随身携带的扫描仪,把这座积木城堡变成可操作的结构图纸;评测时,再把图纸和官方说明书比对,用 UAS、LAS 量出准确率。 学完这篇,你会发现句法分析并不是理论研究,而是很多真实 NLP 工程的第一步:从客服机器人抽取订单意图,到知识图谱抽取“谁发布了什么”,都和这张结构图有关。
句法分析是文本从“词序列”走向“结构化语义”的第一步,掌握它,你就能为问答、抽取、翻译等下游任务搭好稳定骨架。对 NLP 从业者而言,这是文本预处理阶段最能拉开差距的硬技能。
可视化演示
展示依存句法的词间弧线关系、成分句法的层次语法树结构,及两种解析方式的并排对比。
本节配有交互动效(进入视口后自动加载,约 3KB)。
依存句法分析 弧线从核心词指向依存词 根节点sat是句子中心谓词 head \u2192 dependent 扁平结构揭示词间修饰关系
句法分析概述
拿到一堆积木时,你首先会做什么?大概率是先看说明书:城堡分几层,哪里是门,哪里是塔楼。句法分析之于机器,就像是给“句子城堡”找到说明书。它把一维的词序列转成有父子关系的树状结构,让“爱”不再只是第三个词,而是整句话的主心骨。
所谓语法树,就是句法分析的核心产物。树的根通常是整句核心(例如谓词),边则表示词或短语之间如何组合。以“我 爱 NLP”为例,“爱”是根节点,指向“我”和“NLP”,一个表示施动者,一个表示受动者。树不是凭空生成的,在它之前机器通常还要做两件事:分词和词性标注。分词把句子切成积木块,词性标注给每块积木贴上“名词”“动词”的标签,句法分析再把贴好标签的积木按规则拼接起来。
这一节最重要的理解是:句法分析的输入是词序列,输出是结构树。结构树把线性顺序变成了层级关系,方便后续程序直接问“这句话的主语是谁”“宾语是什么”。可以说,它是文本从“一串字”变成“可计算的命题”的枢纽。
当然,说明书不止一种。有人喜欢看承重关系,有人喜欢看模块划分,于是就有了后面两节:依存句法和成分句法。两种视角并不矛盾,就像同一座城堡,既可以用受力图描述,也可以用装配图描述。
依存句法
先看第一种说明书:承重图。城堡里,每一块不是承重墙的砖都会被某块“上级”砖托住,而最上面那根主梁承受全屋重量。依存句法把这种关系搬到句子上:每个词都有一个支配词(head),除根节点外,每个词都从属于另一个词。
在“我爱 NLP”中,“爱”是根节点(root);“我”以 nsubj(主语)关系挂在“爱”下面;“NLP”以 dobj(宾语)关系挂在“爱”下面。这样一条条带箭头的依存弧,就组成了一棵依存树。相比成分句法,依存句法更强调“谁依赖谁”,而不太关心“哪些词组成一个短语”,所以它非常擅长回答“谁对谁做了什么”。
现代依存句法模型通常用打分的方式找最优树:对句子中每一个可能的父子词对,模型都算出一个置信度,然后选择总体得分最高的那棵结构树。用公式可以写成:
把公式翻译回乐高语言:你要在所有“拼接方案”里,找一种最能用已有积木搭建、最符合常规结构受力逻辑的方案。依存树就是这份受力图。
- 句子 S 与候选树 TS 是待分析的词序列,T 是某棵候选依存树,可以看作一组依存边的集合。
- 依存弧 (h,m)从支配词 h 指向从属词 m 的一条有向边,表示“m 挂在 h 下面”。
- 标签概率 p(r_{h,m}\mid S)模型对该弧携带句法关系标签 r 的置信度,例如主语、宾语。
- 连乘 Π把所有弧的得分乘起来,代表整棵树作为句子解释的合理程度。
- argmax 输出从所有候选树中选择总分最高的一棵,作为最终依存树。
成分句法
第二种说明书是装配图。它不直接回答“谁托着谁”,而是先把城堡分成大模块:塔楼、城墙、主楼;再把塔楼拆成窗户、砖块、屋顶。成分句法正是这样一层层“套盒子”的。
给定“我爱 NLP”,成分句法会得到一棵成分树:S(句子)下面分出 NP(名词短语“我”)和 VP(动词短语“爱 NLP”);VP 又继续拆成 V(动词“爱”)和 NP(名词短语“NLP”)。每个内部节点都是一个短语,叶子才是真正的词。
这种嵌套拆解可以用上下文无关文法(CFG)描述。CFG 提供一组“重写规则”,告诉计算机一个大结构可以替换成哪些小结构。例如:
装配图虽然更细致,但要维护很多语法规则,代价也更高;它和承重图一样,只是观察城堡的一个角度,并不互相替代。
- 起始符 SS 代表一个完整的句子,它是整棵成分树的根。
- 规则 S → NP VP一个句子可以拆成“名词短语 + 动词短语”两大块,相当于城堡先分成塔楼和城墙。
- 规则 VP → V NP动词短语继续展开为“动词 + 名词短语”,这里“爱 NLP”就满足这个结构。
- 规则 NP → N名词短语可以继续展开为名词,例如“我”或“NLP”。
主流工具
手动画语法树太累,幸好有“扫描仪”一样的现成工具。spaCy 是工业界最常见的扫描仪:加载快、调用简单,开箱即用;stanza 则更接近学术界的万能工具箱,对多语言支持更好,还能同时给出依存树和成分树。
用 spaCy 做依存句法分析,只需要三行核心逻辑:加载模型、把句子丢给模型、遍历 token 的 head 和 dep_。中文用户可以用 zh_core_web_sm 这类预训练模型,stanza 同样能处理中文。对刚入门的人,spaCy 的 API 最友好;对想要更全面结构的场景,stanza 更合适。
快速上手时要注意:模型是“包装好的积木包”,下载后直接调用 nlp(text) 即可;不要再自己写分词和词性规则,工具会按预训练 pipeline 自动完成。你需要关心的,是把结构树取出来可视化,并落到下游任务中。扫描仪拿到手后,下一步要判断它扫得准不准——这就是评测。
评测方法
扫描仪扫出的图纸永远会有误差,怎么知道准不准?拿着它的输出和官方说明书逐块比对。句法分析的“官方说明书”是人工标注的树库,例如 CoNLL 共享任务和 Universal Dependencies 系列语料。
最常用的两个指标是 UAS(未标记依存准确率)和 LAS(标记依存准确率)。UAS 只看弧头连得对不对,LAS 还要求弧上的关系标签也正确。公式如下:
现代工具的 UAS 往往能达到 85% 以上,LAS 通常低几个点。所以评测很像乐高质检:先看拼接口数量对没对上(UAS),再看每个接口是不是用了正确的卡扣型号(LAS)。
- 分子“正确依存弧”在 UAS 中只要求弧的父节点正确;在 LAS 中要求父节点和关系标签都正确。
- 分母“全部依存弧”模型预测出的所有依存弧数量,包括正确和错误的部分。
- 乘以 100%把比值转换成百分比,便于直观比较。
- 两个指标的关系LAS 比 UAS 更严格,所以通常情况下 LAS 会小于等于 UAS。
应用与选型
结构图纸不是用来收藏的。拿到“谁托着谁”的依存树后,机器可以直接回答“主语是谁”“动作是什么”“宾语是谁”,这正是信息抽取、意图识别和知识图谱构建最需要的中间表示。
选型就像选扫描仪:线上实时服务优先考虑 spaCy,因为它快、内存友好;离线做高精度分析,或者需要成分句法树时,优先考虑 stanza,因为它更强也更容易拿到丰富结构。无论选哪个,都建议先在自己的领域数据上跑一遍 UAS/LAS,看看“官方图纸”上达不达标。
实际工程里,句法分析往往放在“分词 → 词性标注 → 依存解析”这个管道后面。它不负责理解词义,但负责把句子骨架立起来,让下游模型少走弯路。对初学者来说,把一座句子城堡拆成受力图和装配图,是理解自然语言的一把钥匙;这把钥匙会一直陪你走到语义理解那扇门。
AI 应用场景
智能客服意图识别
阶段:文本预处理与语义特征抽取
解决的问题:传统关键词匹配会把“帮我查一下昨天的订单”和“昨天订单有问题吗”都当成“订单”相关,却分不清用户到底要“查询”还是“投诉”。句法分析把“我—查—订单”的依存结构显式抽出后,机器能区分“动词+宾语”的动作对象。
具体案例:某电商客服机器人收到“帮我把张三的订单退款”,依存树让系统找到核心动作“退款”和对象“订单”,再结合命名实体“张三”,自动生成退款工单。
知识图谱事件抽取
阶段:结构化信息抽取
解决的问题:新闻、公告是非结构化文本,人工录入实体关系成本高。依存句法把“主语—谓语—宾语”变成可落库的三元组,让“华为发布Mate60”直接转为(华为,发布,Mate60)。
具体案例:金融舆情系统定期扫描公告,用依存句法提取“公司”“收购”“子公司”的关系,更新产业链知识图谱,省去大量人工标注。
Python 演示
# -*- coding: utf-8 -*-"""依存句法分析小演示首次运行前请安装模型:python -m spacy download en_core_web_sm"""import spacy nlp = spacy.load("en_core_web_sm")text = "Alice loves natural language processing."doc = nlp(text) print("Token\tHead\tRelation")for token in doc: print(f"{token.text}\t{token.head.text}\t{token.dep_}") print("\n依存弧:")for token in doc: if token.dep_ != "ROOT": print(f" {token.head.text} --{token.dep_}--> {token.text}")
nlp = spacy.load("en_core_web_sm")加载预训练模型,相当于给扫描仪装上镜头。doc = nlp(text)执行分词、词性、句法一整套 pipeline,返回结构对象。for token in doc:遍历句子中的每个词符。token.dep_当前词与支配词的关系标签,如 nsubj、dobj。token.head.text当前词在依存树上的支配词,也就是“托着它的上级积木”。if token.dep_ != "ROOT":跳过树根节点,只输出真正有父节点的依存弧。
常见误区
误区我一直以为句法分析就是分词,把“我爱自然语言处理”切成词就算完成。
正解分词只把句子变成零件清单,句法分析还要给出零件间的“拼接图”。同样是“小明看这本书”,分词后如果不分析,机器不知道“看”的对象是“书”,也不知道隐含的主语。
为何常见:分词的“切词”结果肉眼可见,而句法树要额外画出来;初学者容易把可见的前置步骤当成全部。
误区依存句法更简洁,所以成分句法已经过时,根本不用学。
正解两者是不同视角。依存树回答“谁依赖谁”,成分树回答“哪些词组成什么短语”。机器翻译、句法生成常需要成分树,依存句法更适合抽取关系。实际系统经常互补使用。
为何常见:现代工具默认输出依存树,而成分树需要额外配置,导致大家误以为成分句法没用。
误区句法分析工具误差很高,所以结果一定不能信,还不如直接拿原文。
正解现代模型的 UAS 通常能到 90% 左右,对常见句式足够可靠。真正要注意的是长难句和领域迁移,上线前用标注数据评估。
为何常见:偶尔看到一条错误的弧线,就会放大对整体精度的怀疑,而忘记准确率是统计数据。
误区中文不像英文有空格,做句法分析太难,所以只能用英文文本。
正解中文只要先做分词和词性标注,同样能进入依存或成分分析。spaCy 和 stanza 都提供中文预训练模型,线上中文 NLP 系统已经很常见。
为何常见:英文单词之间有天然空格,让人误以为空格是句法分析的前提;其实空格只是便于切词,句法结构分析和语种没有必然绑定。
误区UAS 都到 95% 了,解析质量肯定没问题。
正解UAS 只检查“弧头”对不对,不关心关系标签。如果关系标签总标错,UAS 高但下游抽取照样乱。LAS 更严格,工程上两类指标都要看。
为何常见:人眼看到数字高就安心,忽略了 UAS 的定义里没有包含标签信息。
面试题
Q1. 句法分析任务的输入和输出通常是什么?
- A.输入单词表并输出情感分数
- B.输入句子并输出结构化语法树← 正确答案
- C.输入段落并输出每个字的拼音
- D.输入全文并输出文档主题分类
答案:B。句法分析的核心是从线性句子还原结构树,就像把散装乐高拼出图纸。A 是情感分析,C 是拼音转换,D 是主题分类,都与语法结构无关。
Q2. 依存句法分析中的 root 节点指什么?
- A.整句的核心谓词或根节点← 正确答案
- B.句子中长度最长的名词
- C.总是出现在句首的词
- D.标点符号所在的叶子节点
答案:A。root 是依存树的总根,通常是核心谓词,像城堡的主梁。它不是最长名词、不是句首词,更不是标点。
Q3. 下列哪些属于句法分析的常见结构表示?
- A.依存树← 正确答案
- B.成分树← 正确答案
- C.词频向量
- D.共现矩阵
答案:AB。依存树表示词与词之间的支配关系,成分树表示短语的层次嵌套;两者都是句法结构表示。词频向量和共现矩阵是统计特征,不包含语法结构。
Q4. 在依存句法评测中,UAS 指标衡量什么?
- A.只看弧头是否预测正确← 正确答案
- B.弧头和关系标签都要正确
- C.只看关系标签是否正确
- D.只看整棵树的深度是否一致
答案:A。UAS 全称是 Unlabeled Attachment Score,只判断每个依存弧的“父节点”是否找对,不检查关系标签。LAS 才同时要求弧头和标签正确。
Q5. 关于 spaCy 与 stanza,下列说法正确的是?
- A.两者都能输出成分句法树
- B.spaCy 偏速度,stanza 可出成分树← 正确答案
- C.stanza 只能处理英文语料
- D.spaCy 不能切分中文词
答案:B。spaCy 以工程速度见长,主要输出依存树;stanza 支持多语言,也能产生成分树。A 错在把 spaCy 也当成成分树工具,C、D 与事实不符。
Q6. 句法分析之前通常会做哪些预处理?
- A.分词← 正确答案
- B.词性标注← 正确答案
- C.依存树训练
- D.情感分类
答案:AB。分词把句子切成积木,词性标注给积木贴标签,都是句法分析的常见前置步骤。依存树训练是句法分析本身,情感分类是另一个任务。
Q7. LAS 与 UAS 的核心差异是什么?
- A.LAS 只看弧头是否正确
- B.LAS 要求弧头与关系标签都正确← 正确答案
- C.LAS 要求整棵标准树完全一致
- D.LAS 只统计所有叶子节点
答案:B。LAS 在 UAS 基础上多检查了关系标签,所以更严格。它不要求整棵树完全一致,也不是只看叶子节点。
Q8. 关于依存句法与成分句法,以下说法正确的有?
- A.依存句法关注词间支配关系← 正确答案
- B.成分句法强调短语层次嵌套← 正确答案
- C.两者可以互相补充使用← 正确答案
- D.成分句法不关注短语边界
答案:ABC。依存句法回答谁依赖谁,成分句法回答哪些词组成短语。两种结构可以互补,很多系统同时使用。D 说反了,成分句法恰恰非常关注短语边界。
Q9. 对于“小明喜欢学习”,依存句法最可能的 root 是?
- A.小明
- B.喜欢← 正确答案
- C.学习
- D.没有root
答案:B。“喜欢”是全句的核心谓词,支配“小明”和“学习”,所以最可能是 root。学习虽然也是动词,但在这里扮演“喜欢”的宾语成分。
Q10. 在句法分析工程选型中,合理的做法有哪些?
- A.线上低延迟优先使用spaCy← 正确答案
- B.离线高精度可选stanza← 正确答案
- C.上线前用标注数据评测← 正确答案
- D.所有任务必须做成分句法
答案:ABC。选型要权衡速度和精度,spaCy 适合线上,stanza 适合离线精耕,评测更是必需品。D 把成分句法绝对化了,实际任务不一定需要它。