文法分析

本文深入介绍了文法分析的方法,包括递归下降语法分析(RDP)、Nullable、FIRST和FOLLOW集合的计算,以及LL(1)、LR(0)、SLR、LR(1)和LALR(1)文法分析。通过实例展示了分析预测表的构造,并提及了使用Bison工具进行语法分析的基础知识。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1、递归下降语法分析(RDP)

我们知道,对于一个CFG而言,不管规则多么复杂,规则集中总是会有非终结符到终结符的简单推导,就像递归中的出口一样。例如:

这样的特点是递归下降法能够顺利执行递归的基本条件。

RDP做的事情就是把每个非终结符看作是函数,从这个非终结符推导出的规则是函数体。例如:

可以看到,函数体内部的书写范式是:

case 终结符{eat(终结符);处理下一个;}

RDP是一种预测分析,预测的意思是:接下来要做什么可以通过case后面那个终结符知道。如果一条规则中,->后面的非终结符是不明确的,RDP就失效了,例如:

A->A+B

A->A-B

A->a

B->b

函数A应写作:

void A(void){

    switch(tok){

    case ?:A();eat(+);B();

    case ?:A();eat(-);B();

    case a:eat(a)

    }

}

2、Nullable、FIRST和FOLLOW

为方便后面的讨论(例如,将递归下降法表示成一张表),引入三个定义:

(1)Nullable的定义:

若非终结符A可以推导出空串,则Nullable(A)为真,表示A是"可空的"。

(2)FIRST的定义:

FIRST(A)表示非终结符A推导的规则中,->后面的第一个终结符;

FIRST(ABC...)=FIRST(A)∪FIRST(B)∪FIRST(C)∪...,如果ABC是可空的。

(3)FOLLOW的定义:

对于非终结符A,如果在任意推导中出现At,其中t是终结符,那么t∈FOLLOW(A),如果是ABCt这种情况,但BC是可空的,那么也有t∈FOLLOW(A)

例如:

 

Nullable

FIRST

FOLLOW

X

yes

a c

a c d

Y

yes

c

a c d

Z

no

a c d

 

虽然可以通过观察法找到答案但是形式化的计算更不容易出错,在知道了

Nullable以后,我们完全可以从定义出发,列式计算,例如:

因为X,Y都是可空的,则FIRST(Z)={d}∪FIRST(X)∪FIRST(Y)。

计算FOLLOW同样有一些捷径,例如X的FOLLOW,因为观察到规则集中有XYZ,那么Y的FIRST一定是X的FOLLOW的子集,又因为Y是可空的,所以Z的FIRST也一定是X的FOLLOW的子集,于是可毫不费力地写出{a c d}

3、构造分析预测表

由此可以得到2中文法对应的表:

 

A

c

d

X

X->a

X->Y

X->Y

X->Y

Y

Y->

Y->

Y->c

Y->

实验2 文法的读入、判定和处理 一、实验目的 熟悉文法的结构,了解文法在计算机内的表示方法。 二、实验内容 1、 设计一个表示文法的数据结构; 2、 从文本文件中读入文法,利用定义的数据结构存放文法,并输出; 3、 本实验结果将来还有用。 三、实验要求 1、 了解文法定义的4个部分: G(Vn, Vt, S, P) Vn 文法的非终结符号集合,在实验中用大写的英文字母表示; Vt 文法的终结符号集合,在实验中用小写的英文字母表示; S 开始符号,在实验中是Vn集合中的一个元素; P 产生式,分左部和右部,左部为非终结符号中的一个,右部为终结符号或非终结符号组成的字符串,如S->ab|c 2、 根据文法各个部分的性质,设计一个合理的数据结构用来表示文法, 1) 若使用C语言编写,则文法可以设计成结构体形式,结构体中应包含上述的4部分, 2) 若使用C++语言或java语言编写,则文法可以设计成文法类形式,类中至少含有4个数据成员,分别表示上述4个部分 文法数据结构的具体设计由学生根据自己想法完成,并使用C或C++语言或Java实现设计的数据结构。 3、 利用完成的数据结构完成以下功能: 1) 从文本文件中读入文法文法事先应写入文本文件); 2) 根据文法产生式的结构,分析文法的4个部分,分别写入定义好的文法数据结构的相应部分; 3) 整理文法的结构,判断该文法文法类型,是否为0型,1型,2型或3型文法,并输出判断结果; 4) 在计算机屏幕或者文本框中输出文法文法输出按照一个非终结符号一行,开始符号引出的产生式写在第一行,同一个非终结符号的候选式用“|”分隔的方式输出。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值