编译原理5自底向上的语法分析_第1页
编译原理5自底向上的语法分析_第2页
编译原理5自底向上的语法分析_第3页
编译原理5自底向上的语法分析_第4页
编译原理5自底向上的语法分析_第5页
已阅读5页,还剩96页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、Part5Part5语法分析语法分析授课:胡静授课:胡静自底向上的语法分析概述自底向上的语法分析概述目录目录自底向上语法分析是一个更加强大的分析技术。自底向上语法分析是一个更加强大的分析技术。LR文法文法比比LL描述能力更强描述能力更强构造程序的最右推导构造程序的最右推导几乎所有的程序设计语言都是左递归的几乎所有的程序设计语言都是左递归的更加容易描述程序设计语言的语法。更加容易描述程序设计语言的语法。移进移进-归约分析归约分析LR文法的语法分析器文法的语法分析器语法生成器的自动生成器语法生成器的自动生成器 (e.g., yacc)自顶向下自顶向下vsvs自底向上自底向上自底向上:只需要对当前的

2、输入给出足够的语法树的自底向上:只需要对当前的输入给出足够的语法树的部分就行部分就行自底向上的语法分析自底向上的语法分析较常用的自底向上语法分析法较常用的自底向上语法分析法移动归约分析法移动归约分析法用栈实现移动归约分析用栈实现移动归约分析最易于实现的移动归约分析法最易于实现的移动归约分析法算符优先分析法算符优先分析法算符优先分析法定义、优先分析表的确定、优先函数的定义算符优先分析法定义、优先分析表的确定、优先函数的定义使用算符优先关系进行分析使用算符优先关系进行分析算符优先分析中的错误恢复算符优先分析中的错误恢复最一般的移动归约分析方法最一般的移动归约分析方法LR分析法分析法自底向上语法分析

3、概述自底向上语法分析概述自底向上的语法分析方法,也称为移动归约分析法。自底向上的语法分析方法,也称为移动归约分析法。最易于实现的一种移动归约分析方法,叫做算符优先分析法,最易于实现的一种移动归约分析方法,叫做算符优先分析法,而更一般的移动归约分析方法叫做而更一般的移动归约分析方法叫做LR分析法,分析法,LR分析法可以用分析法可以用作许多自动的语法分析器的生成器。作许多自动的语法分析器的生成器。移动归约分析法为输入串构造分析数时是从叶结点(底端)移动归约分析法为输入串构造分析数时是从叶结点(底端)开始,向根结点(顶端)前进。开始,向根结点(顶端)前进。我们可以把该过程看成是把输入串我们可以把该过

4、程看成是把输入串“归约归约”成文法开始符号的成文法开始符号的过程。过程。在每一步归约中,如果一个子串和某个产生式的右部匹配,则用在每一步归约中,如果一个子串和某个产生式的右部匹配,则用该产生式的左部符号代替该子串。该产生式的左部符号代替该子串。如果每一步都能恰当的选择子串,我们就可以得到最右推导的逆如果每一步都能恰当的选择子串,我们就可以得到最右推导的逆过程。过程。 移进移进- -归约分析归约分析分析就是移进和归约动作的序列分析就是移进和归约动作的序列移进:将当前扫描的移进:将当前扫描的token移动到堆栈中。移动到堆栈中。归约:将栈顶的符号串归约:将栈顶的符号串 移除,用非终结符移除,用非终

5、结符X代替,代替,这对应着产生式这对应着产生式A (pop , push A)短语、直接短语、句柄的定义:短语、直接短语、句柄的定义:文法文法GS,是文法是文法G的一个句型,的一个句型,S=*A且且A=+则称则称是句型是句型相对于非终结符相对于非终结符A的短语。若有的短语。若有A 则称则称是句型是句型相对于该规则相对于该规则A的直接短语。一个句型的最左直接短语称为该句的直接短语。一个句型的最左直接短语称为该句型的句柄。型的句柄。用子树解释短语,直接短语,句柄用子树解释短语,直接短语,句柄: :短语:一棵子树的所有叶子自左至右排列起来形成一短语:一棵子树的所有叶子自左至右排列起来形成一个相对于子

6、树根的短语。个相对于子树根的短语。直接短语:仅有父子两代的一棵子树,它的所有叶子直接短语:仅有父子两代的一棵子树,它的所有叶子自左至右排列起来所形成的符号串。自左至右排列起来所形成的符号串。句柄:一个句型的分析树中最左那棵只有父子两代的句柄:一个句型的分析树中最左那棵只有父子两代的子树的所有叶子的自左至右排列。子树的所有叶子的自左至右排列。例如,对表达式文法例如,对表达式文法GE和句子和句子a1+a2*a3,挑选出,挑选出推导过程中产生的句型中的短语,直接短语,句柄。推导过程中产生的句型中的短语,直接短语,句柄。EE+TE+T*FE+T*a3 E+F*a3 E+a2*a3 T+a2 *a3 F

7、+a2*a3E+T T*F,E+T*F a3,T*a3,E+T*a3 a3,F,F*a3,E+F*a3 a3,a2,a2*a3, E+a2*a3a3,a2,T, a2*a3, T+a2*a3a3,a2,F, a2*a3, F+a2*a3a1, a2, a3, a2 * a3 a1+ a2 *a3EE+TTFa1T*FFa2a3a1+a2 *a3短语短语 移动归约分析法相关概念移动归约分析法相关概念规范归约规范归约文法的最右推导为规范推导,自底向上分析是自顶向下最右推导的逆文法的最右推导为规范推导,自底向上分析是自顶向下最右推导的逆过程,叫规范归约过程,叫规范归约句柄句柄直观来看:一个符号串的直

8、观来看:一个符号串的“句柄句柄”是和一个产生式右部匹配的子串,是和一个产生式右部匹配的子串,而且把它归约到该产生式左部的非终结符代表了最右推导逆过程的一而且把它归约到该产生式左部的非终结符代表了最右推导逆过程的一步。步。形式定义:右句型(最右推导可得到的句型)形式定义:右句型(最右推导可得到的句型)的句柄是一个产生式的句柄是一个产生式A以及以及的一个位置,在该位置可以找到串的一个位置,在该位置可以找到串,而且用,而且用A代替代替可以得到可以得到的最右推导的前一个右句型的最右推导的前一个右句型对于有二义性的文法而言,由于最右推导不一定,则句柄不一定唯一。对于有二义性的文法而言,由于最右推导不一定

9、,则句柄不一定唯一。只有当文法没有二义性时,每个右句型才只有一个句柄。只有当文法没有二义性时,每个右句型才只有一个句柄。句柄剪裁句柄剪裁通过通过“剪裁句柄剪裁句柄”可以得到最右推导的逆过程可以得到最右推导的逆过程在归约过程中用到的产生式序列的逆序就是输入串的最右推导在归约过程中用到的产生式序列的逆序就是输入串的最右推导(1)S aABe (2)A b (3)A Abc (4)B dSaABeaAdeaAbcdeabbcde步骤步骤符号栈符号栈输入符号串输入符号串 动作动作1$abbcde$移动移动2$a bbcde$移动移动3$ab bcde$归约归约(2)4$aA bcde$移动移动5$aA

10、b cde$移动移动6$aAbc de$归约(归约(3)7$aA de$移动移动8$aAd e$归约归约(4)9$aAB e$移进移进10$aABe $归约归约(1)11$S $接受接受移动归约分析中需要解决的问题移动归约分析中需要解决的问题定位右句型中将要归约的子串(可归约串)定位右句型中将要归约的子串(可归约串)在用堆栈实现时,这个子串总是在栈顶。语法分析器在用堆栈实现时,这个子串总是在栈顶。语法分析器不需要深入到栈中去寻找句柄不需要深入到栈中去寻找句柄选择产生式对选定的串进行归约选择产生式对选定的串进行归约如果选定的子串是多个产生式的右部,要确定选择哪如果选定的子串是多个产生式的右部,要

11、确定选择哪个产生式进行归约个产生式进行归约移动归约分析过程中的冲突移动归约分析过程中的冲突根据栈中的内容和下一个输入符号不能决定是移动还根据栈中的内容和下一个输入符号不能决定是移动还是归约(移动是归约(移动-归约冲突)归约冲突)不能决定按哪一个产生式进行归约(归约不能决定按哪一个产生式进行归约(归约-归约冲突)归约冲突)算符优先分析法算符优先分析法 算符优先分析法算符优先分析法算符文法的定义:算符文法的定义:所有产生式的右部都不是所有产生式的右部都不是或两个相邻的非终结符或两个相邻的非终结符设有一个文法设有一个文法G,如果,如果G中没有形如中没有形如ABC的产生式,其中的产生式,其中B和和C为

12、非终结符,则称为非终结符,则称G为算符文法为算符文法(Operator Grammar)也称也称OG文法文法.算符优先文法的特点:算符优先文法的特点:一旦我们构造了算符优先语法分析器,就可以忽略原来的文法,一旦我们构造了算符优先语法分析器,就可以忽略原来的文法,栈中的非终结符仅仅作为与这些非终结符相关的属性的占位符栈中的非终结符仅仅作为与这些非终结符相关的属性的占位符难以处理像减号这样有不同优先级的符号难以处理像减号这样有不同优先级的符号由于分析的语言的文法和算符优先语法分析器本身的关系不是很由于分析的语言的文法和算符优先语法分析器本身的关系不是很紧密,所以不能肯定语法分析器接受的就是所期望的

13、语言紧密,所以不能肯定语法分析器接受的就是所期望的语言算符优先关系的定义算符优先关系的定义a的优先级低于的优先级低于ba b:文法中有形如:文法中有形如A ABbBb的产生式的产生式, ,而而B B+aa或或B B+aCaC算符的优先关系是有序的算符的优先关系是有序的如果如果a b,不能推出,不能推出b b,有可能,有可能b a如果如果a b, b c,不一定,不一定a c算符优先关系定义(续算符优先关系定义(续1 1)a b,则存在语法子树如下,则存在语法子树如下其中,其中,为为或者或者C C,a a和和b b不在同一个句柄中,不在同一个句柄中,a a先被归约先被归约A A B Bb b P

14、 Pa a最左素短语最左素短语一个算符优先文法一个算符优先文法G的任何句型的最左素短语是满足的任何句型的最左素短语是满足如下条件的最左子串如下条件的最左子串 NjajNiaiNi+1,aj-1ai+1使用算符优先关系使用算符优先关系算符优先关系主要用于界定右句型的句柄算符优先关系主要用于界定右句型的句柄标记句柄标记句柄的右端。的右端。发现句柄的过程:发现句柄的过程:从左端开始扫描串,直到遇到第一个从左端开始扫描串,直到遇到第一个为止。为止。向左扫描,跳过所有的向左扫描,跳过所有的=,直到遇到一个,直到遇到一个为止。为止。句柄包括从上一步遇到的句柄包括从上一步遇到的左部之间的所左部之间的所有符号

15、,包括介于期间或者两边的非终结符有符号,包括介于期间或者两边的非终结符非终结符的处理非终结符的处理因为非终结符不能影响语法分析,所以不需要区分它因为非终结符不能影响语法分析,所以不需要区分它们,于是只用一个占位符来代替它们们,于是只用一个占位符来代替它们算符优先分析算法算符优先分析算法算法的主体思想算法的主体思想用栈存储已经看到的输入符号,用优先关系指导移动用栈存储已经看到的输入符号,用优先关系指导移动归约语法分析器的动作归约语法分析器的动作如果栈顶的终结符和下一个输入符之间的优先关系是如果栈顶的终结符和下一个输入符之间的优先关系是关系,就调用归约关系,就调用归约算法描述算法描述输入:输入字符

16、串输入:输入字符串和优先关系表和优先关系表输出:如果输出:如果是语法产生的一个句子,则输出其用来是语法产生的一个句子,则输出其用来归约的产生式;如果有错误,则转入错误处理归约的产生式;如果有错误,则转入错误处理规范归约和算符优先归约规范归约和算符优先归约句型句型#i+i#的规范归约过程的规范归约过程步骤步骤符号栈符号栈剩余输入串剩余输入串 句柄句柄 归约用产生式归约用产生式1# i+i# 2#i +i# i Pi4#F +i# F TF5#T +i# T ET6#E +i#7#E+ i#8#E+i # i Pi10#E+F # F TF11#E+T # E+T EE+T12#E # 接受接受E

17、 = #E# = #E+T# = #E+F# = #E+P# = #E+i# = #T+i# = #F+i# = #P+i# = #i+i#3#P +i# P FP9#E+P # P FP规范归约和算符优先归约规范归约和算符优先归约句型句型#i+i#的算符优先归约过程的算符优先归约过程步骤步骤栈栈 优先关系优先关系 当前符号当前符号 剩余符号串剩余符号串 动作动作1 1# # i +i# + i# + i# 归约归约3 3#P#P + i# + i# 移进移进3 3#P+#P+ i # # # 归约归约4 4#P+P#P+P # # 归约归约4 4#E#E = # = # 接受接受算符优先分析

18、法优缺点算符优先分析法优缺点由于算符优先分析并未对文法的非终结符定义优先关由于算符优先分析并未对文法的非终结符定义优先关系,所以就无法发现由单个非终结符组成的系,所以就无法发现由单个非终结符组成的“可归约可归约串串”。也就是说,在算符优先归约过程中,我们无法用那些也就是说,在算符优先归约过程中,我们无法用那些右部仅含一个非终结符的产生式(称为单非产生式,右部仅含一个非终结符的产生式(称为单非产生式,如如PQ)进行归约。这样,算符优先分析比规范归)进行归约。这样,算符优先分析比规范归约要快很多。这既是算符优先分析的优点,也是它的约要快很多。这既是算符优先分析的优点,也是它的缺点。缺点。忽略非终结

19、符在归约过程中的作用,存在某种危险性,忽略非终结符在归约过程中的作用,存在某种危险性,可能导致把本来不成句子的输入串误认为是句子。可能导致把本来不成句子的输入串误认为是句子。 优先函数优先函数优先函数的计算方法优先函数的计算方法1.f(a) g(b),如果,如果a g(b),如果,如果a b优先函数的问题优先函数的问题使得优先关系表中的空白项是模糊的使得优先关系表中的空白项是模糊的使得错误的发现被推迟使得错误的发现被推迟优先关系表的存储方式优先关系表的存储方式矩阵表示:准确直观;需要大量内存空间矩阵表示:准确直观;需要大量内存空间(n+1)(n+1)2 2优先函数:需要内存空间小优先函数:需要

20、内存空间小2(n+1)2(n+1);不利于出错处理;不利于出错处理优先函数的构造算法优先函数的构造算法输入:算符优先表输入:算符优先表输出:表示输入矩阵的优先函数或指出它不存在输出:表示输入矩阵的优先函数或指出它不存在方法:方法:为每个终结符(包括为每个终结符(包括#)创建)创建fa和和ga。并以其作为结点,画出。并以其作为结点,画出2n个结点个结点如果如果a b或者或者a = b,则画一条从,则画一条从fa到到gb的箭弧的箭弧如果如果a b或者或者a = b,则画一条从,则画一条从gb到到fa的箭弧的箭弧如果构造的图中有环路,则不存在优先函数;如果没有环路,则如果构造的图中有环路,则不存在优

21、先函数;如果没有环路,则将将f(a)设为从设为从fa开始的最长路径的长度;开始的最长路径的长度;g(a)为从为从ga开始的最长路开始的最长路径的长度。径的长度。检查是否一致!检查是否一致!实例说明实例说明i*+$i*+$=figig*f*f+g+g#f#i*+$fg45432100检查是否一致!检查是否一致!算符优先分析中的错误恢复算符优先分析中的错误恢复算符优先分析器能发现的语法错误算符优先分析器能发现的语法错误如果栈顶的终结符和当前输入之间没有优先关系(如如果栈顶的终结符和当前输入之间没有优先关系(如果用优先函数存储,这个错误不能发现)果用优先函数存储,这个错误不能发现)如果发现句柄,但句

22、柄不是任何产生式的右部如果发现句柄,但句柄不是任何产生式的右部归约时的错误处理归约时的错误处理给出相应的具有描述性的出错信息给出相应的具有描述性的出错信息试图通过插入、删除来获得句柄试图通过插入、删除来获得句柄一个加入了出错处理的优先矩阵一个加入了出错处理的优先矩阵E1:缺少整个表达式:缺少整个表达式把把id插入输入字符串中插入输入字符串中输出诊断信息输出诊断信息Missing operandE2:表达式以右括号开始:表达式以右括号开始从输入中删除从输入中删除 )输出诊断信息输出诊断信息Unbalanced right parenthesisE3:id/)后面跟后面跟id/(把把+插入输入字符

23、串插入输入字符串输出诊断信息输出诊断信息Missing operatorE4:表达式以左括号结束:表达式以左括号结束从栈中弹出从栈中弹出(输出诊断信息输出诊断信息Missing right parenthesisid()$idE3E3($aABeaAdeaAbcdeabbcde步骤步骤符号栈符号栈输入符号串输入符号串 动作动作1$abbcde$移动移动2$a bbcde$移动移动3$ab bcde$归约归约(2)4$aA bcde$移动移动5$aAb cde$移动移动6$aAbc de$归约(归约(3)7$aA de$移动移动8$aAd e$归约归约(4)9$aAB e$移进移进10$aABe

24、 $归约归约(1)11$S $接受接受LRLR语法分析算法语法分析算法 LR分析的基本思想是,在规范归约过程中,一方面分析的基本思想是,在规范归约过程中,一方面记住已移进和归约出的整个符号串,即记住记住已移进和归约出的整个符号串,即记住“历史历史”,另一方面根据所用的产生式推测未来可能碰到的输入另一方面根据所用的产生式推测未来可能碰到的输入符号,即对未来进行符号,即对未来进行“展望展望”。当一串貌似句柄的符号串呈现于分析栈的顶端时,我当一串貌似句柄的符号串呈现于分析栈的顶端时,我们希望能够根据所记载的们希望能够根据所记载的“历史历史”和和“展望展望”以及以及“现实现实”的输入符号等三方面的材料

25、,来确定栈顶的的输入符号等三方面的材料,来确定栈顶的符号串是否构成相对某一产生式的句柄。符号串是否构成相对某一产生式的句柄。 LRLR语法分析器的结构语法分析器的结构一个一个LR分析器实质上是一个带先进后出存储器(栈)的确定分析器实质上是一个带先进后出存储器(栈)的确定有限状态自动机。有限状态自动机。栈栈LR分分析析程程序序actiongoto输输出出输输入入串串a1SmS1S0XmX1#aian#分分析析表表LRLR语法分析器的结构语法分析器的结构栈栈我们将把我们将把“历史历史”和和“展望展望”材料综合的抽象成某些材料综合的抽象成某些“状状态态”,存放在栈里。栈里的每个状态概括了从分析开始直

26、到,存放在栈里。栈里的每个状态概括了从分析开始直到某一归约阶段的全部某一归约阶段的全部“历史历史”和和“展望展望”资料。资料。 SmS1S0XmX1X0栈顶栈顶状态状态符号符号LRLR语法分析器的结构语法分析器的结构分析表分析表ACTIONs ,a规定了当前状态规定了当前状态s面临输入符号面临输入符号a时应采时应采取什么动作。取什么动作。GOTOs, X规定了状态规定了状态s面对文法符号面对文法符号X(终结符或(终结符或非终结符)时下一个状态是什么。非终结符)时下一个状态是什么。 LRLR语法分析器的结构语法分析器的结构ACTIONACTION表表每一项每一项ACTIONs,a所规定的动作不外

27、是下述四种可所规定的动作不外是下述四种可能之一。能之一。移进:把移进:把(s,a)的下一个状态的下一个状态s=GOTOs,a和输入符号和输入符号a推进栈,下一个输入符号变成现行输入符号推进栈,下一个输入符号变成现行输入符号归约:指用某一个产生式归约:指用某一个产生式A进行归约。假若进行归约。假若的长的长度为度为r,归约的动作是,归约的动作是A,去除栈顶的,去除栈顶的r个项,使状态个项,使状态Sm-r变成栈顶状态,然后把(变成栈顶状态,然后把(Sm-r, A)的下一个状态)的下一个状态s=GOTOSm-r, A和文法符号和文法符号A推进栈。推进栈。接受:宣布分析成功,停止分析器的工作。接受:宣布

28、分析成功,停止分析器的工作。报错:发现源程序含有错误,调用出错处理程序。报错:发现源程序含有错误,调用出错处理程序。 LRLR语法分析器分析过程举例语法分析器分析过程举例文法文法G:(1)E E+T (2)E T(3)T T*F (4)T F (5)F (E)(6)F i状态状态ACTIONGOTOi+*()#ETF0S5S41231S6acc2r2S7r2r23r4r4r4r44S5S48235r6r6r6r66S5S4937S5S4108S6S119r1S7r1r110r3r3r3r311r5r5r5r5对上述例子的分析对上述例子的分析LR语法分析器不需要扫描整个栈就可以知道什么时语法分析

29、器不需要扫描整个栈就可以知道什么时候句柄出现在栈顶。栈顶的状态符号包含了所需要的候句柄出现在栈顶。栈顶的状态符号包含了所需要的一切信息。一切信息。 请注意一个非常重要的事实:如果仅由栈的内容和现请注意一个非常重要的事实:如果仅由栈的内容和现实的输入符号就可以识别一个句柄,那么就可以用一实的输入符号就可以识别一个句柄,那么就可以用一个有限自动机自底向上扫描栈的内容和检查现行输入个有限自动机自底向上扫描栈的内容和检查现行输入符号来确定呈现于栈顶的句柄是什么(当栈顶呈现一符号来确定呈现于栈顶的句柄是什么(当栈顶呈现一个句柄时)。个句柄时)。 实际上,实际上,LR分析表的分析表的goto函数就是这样一

30、个有限自函数就是这样一个有限自动机,只是它不需要每次移动都读栈。动机,只是它不需要每次移动都读栈。 LRLR文法与文法与LLLL文法的区别文法的区别LL文法要求每个非终结符的所有候选首字符均不相文法要求每个非终结符的所有候选首字符均不相同,因为预测程序认为,一旦看到首符之后就看准了同,因为预测程序认为,一旦看到首符之后就看准了该用哪一个产生式进行推导。该用哪一个产生式进行推导。但但LR分析程序只有在看到整个右部所推导的东西之分析程序只有在看到整个右部所推导的东西之后才认为是看准了归约方向。因此,后才认为是看准了归约方向。因此,LR方法比方法比LL方方法更加一般化。法更加一般化。 LR(0)LR

31、(0)项目集族和项目集族和LR(0)LR(0)分析表的构造分析表的构造 相关概念:相关概念:前缀:字的前缀是指该字的任意首部。前缀:字的前缀是指该字的任意首部。字字abc的前缀有的前缀有、a、ab、abc。活前缀:指规范句型的一个前缀,这种前缀不含句柄活前缀:指规范句型的一个前缀,这种前缀不含句柄之后任何符号。之所以称为活前缀,是因为在右边添之后任何符号。之所以称为活前缀,是因为在右边添加一些符号之首,就可以使它称为一个规范句型。加一些符号之首,就可以使它称为一个规范句型。在在LR分析工作过程中的任何时候,栈里的文法符号分析工作过程中的任何时候,栈里的文法符号(自栈底而上)(自栈底而上)X0

32、X1 Xm应该构成活前缀,把输入应该构成活前缀,把输入串的剩余部分配上之后即应成为规范句型。串的剩余部分配上之后即应成为规范句型。只要输入串的已扫描部分保持可归约成一个活前缀,那只要输入串的已扫描部分保持可归约成一个活前缀,那就意味着所扫描过的部分没有错误。就意味着所扫描过的部分没有错误。 LR(0)LR(0)项目的定义项目的定义对于一个文法对于一个文法G,我们首先要构造一个,我们首先要构造一个NFA,它能识,它能识别别G的所有活前缀。这个的所有活前缀。这个NFA的每一个状态是下面定的每一个状态是下面定义的一个义的一个“项目项目”。 文法文法G的每一个产生式的右部添加一个圆点称为的每一个产生式

33、的右部添加一个圆点称为G的的一个一个LR(0)项目(简称项目)。例如产生式项目(简称项目)。例如产生式AXYZ对应有四个项目:对应有四个项目:AXYZAXYZAXYZAXYZ 产生式产生式A只对应一个项目只对应一个项目A。 LR(0)LR(0)项目的说明项目的说明直观上说,一个项目指明了在分析过程的某时刻我们直观上说,一个项目指明了在分析过程的某时刻我们看到产生式多大部分。看到产生式多大部分。例如,例如, AXYZ这个项目意味着,我们希望能从后面这个项目意味着,我们希望能从后面输入串中看到可以从输入串中看到可以从XYZ推出的符号串。推出的符号串。AXYZ这个项目意味着,我们已经从输入串中看到这

34、个项目意味着,我们已经从输入串中看到能从能从X推出的符号串,我们希望能进一步看到可以从推出的符号串,我们希望能进一步看到可以从YZ推出的符号串。推出的符号串。 将每个项目看成将每个项目看成NFA的一个状态,我们就可以构造这的一个状态,我们就可以构造这样一个样一个NFA,用来识别文法所有的活前缀。,用来识别文法所有的活前缀。 LR(0)LR(0)项目间的转换规则项目间的转换规则如果状态如果状态i和和j来自同一个产生式,而且状态来自同一个产生式,而且状态j的圆点的圆点只落后于状态只落后于状态i的原点一个位置,的原点一个位置,如状态如状态i为为XX1 Xi-1 XiXn,状态状态j为为XX1 Xi

35、Xi+1Xn,那么就从状态那么就从状态i画一条标志为画一条标志为Xi的弧到状态的弧到状态j。假若状态假若状态i的圆点之后的那个符号为非终结符,的圆点之后的那个符号为非终结符,如如i为为XA,A为非终结符,为非终结符,就从状态就从状态i画画弧到所有弧到所有A状态。状态。NFA的接受状态就是那些圆点出现在最右边的项目。的接受状态就是那些圆点出现在最右边的项目。LR(0)LR(0)项目分类项目分类归约项目归约项目凡圆点在最右的项目,如凡圆点在最右的项目,如A称为一个称为一个“归约项目归约项目” 接受项目接受项目对文法的开始符号对文法的开始符号S的归约项目,如的归约项目,如S称为称为“接受接受”项目。

36、项目。 移进项目移进项目形如形如Aa的项目,其中的项目,其中a为终结符,称为为终结符,称为“移进移进”项目。项目。待约项目待约项目形如形如AB的项目,其中的项目,其中B为非终结符,称为为非终结符,称为“待约待约”项目。项目。 识别识别LR(0)LR(0)活前缀的活前缀的NFANFA举例举例文法文法G:S EE aA | bB A cA | dB cB | d文法的项目有:文法的项目有:14. B cB 15. B cB 16. B cB 3. E aA4. E aA5. E aA6. A cA7. A cA8. A cA11. E bB12. E bB13. E bB17. B d 18. B

37、 d1. S E2. S E 9. A d10. A d 识别识别LR(0)LR(0)活前缀的活前缀的NFANFA举例(续)举例(续)初态初态S E 1句柄识别态句柄识别态E aA5A cA8A d 10E bB13B cB 16B d18句子识别态句子识别态S E 214. B cB 15. B cB 16. B cB 3. E aA4. E aA5. E aA6. A cA7. A cA8. A cA11. E bB12. E bB13. E bB17. B d 18. B d1. S E2. S E 9. A d10. A d 1. S E2. S E 3. E aA4. E aA5.

38、E aA6. A cA7. A cA8. A cA9. A d10. A d 11. E bB12. E bB13. E bB16. B cB 15. B cB 14. B cB 18. B d17. B d EaAcAdbBcBd0. S E E aA E bB2. E aA A cA A d1. S E3. E bB B cB B d4. A cA A cA A d5. B cB B cB B d8. A cA10. A d6. E aA7. E bB11. B d9. B cBbEaccccABdAdddBLR(0)LR(0)项目集规范族的构造项目集规范族的构造用用-CLOSURE(闭包

39、闭包)的办法来构造一个文法的办法来构造一个文法G的的LR(0)项目集规范族。项目集规范族。准备工作:准备工作:假定文法假定文法G是一个以是一个以S为开始符号的文法,我们构造一为开始符号的文法,我们构造一个文法个文法G,它包含整个,它包含整个G,但它引进了一个不出现在,但它引进了一个不出现在G中的非终结符中的非终结符S,并加进一个新产生式,并加进一个新产生式SS,而这个,而这个S是是G的开始符号。那么我们称的开始符号。那么我们称G是是G的拓广文法。的拓广文法。 这样,便会有一个仅含项目这样,便会有一个仅含项目SS的状态,这就是唯的状态,这就是唯一的一的“接受接受”状态。状态。 LR(0)LR(0

40、)项目集规范族的构造项目集规范族的构造假定假定I是文法是文法G的任一项目集,定义和构造的任一项目集,定义和构造I的闭包的闭包CLOSURE(I)的办法是:的办法是: I的任何项目都属于的任何项目都属于CLOSURE(I);若若AB属于属于CLOSURE(I),那么,对任何关于,那么,对任何关于B的产生式的产生式B,项目,项目B也属于也属于CLOSURE(I);重复执行上述两步骤直至重复执行上述两步骤直至CLOSURE(I)不再增大为止。不再增大为止。函数函数GO(I,X)是一个状态转换函数。是一个状态转换函数。第一个变元第一个变元I是一个项目集,是一个项目集,第二个变元第二个变元X是一个文法符

41、号。是一个文法符号。函数值函数值GO(I,X)定义为定义为GO(I,X)=CLOSURE(J),其中其中J=任何形如任何形如AX的项目的项目 | AX属于属于I LR(0)LR(0)项目集规范族举例项目集规范族举例初始状态初始状态I0的项目集规范族:的项目集规范族:S EE aAE bBI1、I2、I3和分别是和分别是GO(I0,E)、 GO(I0,a)和和GO(I0,b)I1是是CLOSURE(SE)=SEI2是是CLOSURE(EaA)=EaA, AcA, AdI3是是CLOSURE(EbB)=EbB, BcB, Bd文法文法G:(0) S E(1) E aA (2) E bB (3) A

42、 cA(4) A d(5) B cB(6) B d0. S E E aA E bB2. E aA A cA A d1. S E3. E bB B cB B d4. A cA A cA A d5. B cB B cB B d8. A cA10. A d6. E aA7. E bB11. B d9. B cBbEaccccABdAdddBLR(0)LR(0)项目集规范族的讨论项目集规范族的讨论有效项目有效项目我们说项目我们说项目A12对活前缀对活前缀1是有效的,其条件是存在规范是有效的,其条件是存在规范推导推导S=*A=12。LR(0)项目集可能出现的冲突项目集可能出现的冲突同一项目可能对好几个活

43、前缀都是有效的(当一个项目出现在同一项目可能对好几个活前缀都是有效的(当一个项目出现在好几个不同的集合中便是这种情况)。好几个不同的集合中便是这种情况)。若归约项目若归约项目A1对活前缀对活前缀1是有效的,则它告诉我们应该是有效的,则它告诉我们应该把符号串把符号串1归于为归于为A。即把活前缀。即把活前缀1变成变成A。若移进项目若移进项目A12对活前缀对活前缀1是有效的,则它告诉我们,句是有效的,则它告诉我们,句柄尚未形成,因此,下一步动作应该是移进。柄尚未形成,因此,下一步动作应该是移进。但是,可能存在这样的情形,对同一活前缀,存在若干项目对但是,可能存在这样的情形,对同一活前缀,存在若干项目

44、对它都是有效的,而且告诉我们应该做的事情各不相同,互相冲它都是有效的,而且告诉我们应该做的事情各不相同,互相冲突。这种冲突通过向前多看几个输入符号,或许能够解决,但突。这种冲突通过向前多看几个输入符号,或许能够解决,但有些冲突却是无法解决的。有些冲突却是无法解决的。 LR(0)LR(0)分析表的构造分析表的构造假如一个文法假如一个文法G的拓广文法的拓广文法G的活前缀识别自动机的的活前缀识别自动机的每个状态(项目集)不存在下述情况:每个状态(项目集)不存在下述情况:既含移进项目又含归约项目。既含移进项目又含归约项目。含多个归约项目。含多个归约项目。则称则称G是一个是一个LR(0)文法。换言之,文

45、法。换言之,LR(0)文法规范族文法规范族的每个项目集不包含任何冲突项目。的每个项目集不包含任何冲突项目。 LR(0)LR(0)分析表的构造分析表的构造假定项目集规范族假定项目集规范族C=I0,I1,In。令每一个项目集。令每一个项目集Ik的下标的下标k作为分析器的状态。分析表的作为分析器的状态。分析表的ACTION子表和子表和GOTO子表可子表可按如下方法构造按如下方法构造令那个包含项目令那个包含项目SS的集合的集合Ik的下标的下标k为分析器的初态。为分析器的初态。 若项目若项目Aa属于属于Ik且且GO(Ik , a)= Ij,a为终结符,置为终结符,置ACTIONk,a为为“把把(j,a)

46、移进栈移进栈”,简记为,简记为“sj”。若项目若项目A属于属于Ik,对任何终结符,对任何终结符a(或结束符或结束符#),置,置ACTIONk,a为为“用产生式用产生式A进行归约进行归约”,简记为,简记为“rj”(假定产生式(假定产生式A是文法是文法G的第的第j个产生式)。个产生式)。若项目若项目SS属于属于Ik,则置,则置ACTIONk,#为为“接受接受”,简记为,简记为“acc”。若若GO(Ik , A)= Ij,A为非终结符,则置为非终结符,则置GOTOk,A=j。分析表中凡不能用规则分析表中凡不能用规则1至至4填入信息的空白格均填上填入信息的空白格均填上“报错标志报错标志”。 0. S

47、E E aA E bB2. E aA A cA A d1. S E3. E bB B cB B d4. A cA A cA A d5. B cB B cB B d8. A cA10. A d6. E aA7. E bB11. B d9. B cBbEaccccABdAdddBSLRSLR分析表的构造分析表的构造SLRSLR语法分析概述语法分析概述LR(0)文法的活前缀识别自动机的每一个状态(项目文法的活前缀识别自动机的每一个状态(项目集)都不含冲突的项目。集)都不含冲突的项目。本节我们要研究一种有点简单本节我们要研究一种有点简单“展望展望”材料的材料的LR分分析法,即析法,即SLR文法。文法。

48、SLR文法构造分析表的主要思想是:许多冲突性的动文法构造分析表的主要思想是:许多冲突性的动作都可能通过考察有关非终结符的作都可能通过考察有关非终结符的FOLLOW集而获集而获解决。解决。 LR(0)LR(0)文法的局限性文法的局限性假定一个假定一个LR(0)规范族中含有如下的一个项目集(状规范族中含有如下的一个项目集(状态)态)I:I=Xb, A, B第一个项目是移进项目,第二、三个项目是归约项目。第一个项目是移进项目,第二、三个项目是归约项目。这三个项目告诉我们应该做的动作各不相同,互相冲这三个项目告诉我们应该做的动作各不相同,互相冲突:突:第一个项目告诉我们应该把下一个符号第一个项目告诉我

49、们应该把下一个符号b移进;移进;第二个项目告诉我们应该把栈顶的第二个项目告诉我们应该把栈顶的归约为归约为A;第三个项目告诉我们应该把栈顶的第三个项目告诉我们应该把栈顶的归约为归约为B。 SLRSLR基本算法基本算法解决冲突的方法是分析所有含解决冲突的方法是分析所有含A和和B的句型,考察集的句型,考察集合合FOLLOW(A)和和FOLLOW(B),如果这两个集合不,如果这两个集合不相交,而且也不包含相交,而且也不包含b,那么当状态,那么当状态I面临输入符号面临输入符号a时,我们可以使用如下策略:时,我们可以使用如下策略:若若a=b,则移进。,则移进。若若aFOLLOW(A),则用产生式,则用产生

50、式A进行归约;进行归约;若若aFOLLOW(B),则用产生式,则用产生式B进行归约;进行归约;此外,报错此外,报错SLRSLR基本算法基本算法假定假定LR(0)规范族的一个项目集规范族的一个项目集I中含有中含有m个移进项目个移进项目A1a11,A2a22,Amamm;同时含有同时含有n个归约项目个归约项目B1,B2,B3,如果集合如果集合 a1, am,FOLLOW(B1),FOLLOW(Bn)两两两两不相交(包括不得有两个不相交(包括不得有两个FOLLOW集合有集合有#),则隐含在),则隐含在I中中的动作冲突可以通过检查现行输入符号的动作冲突可以通过检查现行输入符号a属于上述属于上述n+1个

51、集合个集合中的哪个集合而活的解决:中的哪个集合而活的解决:若若a是某个是某个ai,i=1,2,m,则移进。,则移进。若若aFOLLOW(Bi),i=1,2,m,则用产生式,则用产生式Bi进行归约;进行归约;此外,报错此外,报错这种冲突的解决方法叫做这种冲突的解决方法叫做SLR(1)解决办法。解决办法。 SLRSLR语法分析表的构造算法语法分析表的构造算法首先把首先把G拓广为拓广为G,对,对G构造构造LR(0)项目集规范族项目集规范族C和活前缀和活前缀识别自动机的状态转换函数识别自动机的状态转换函数GO。函数。函数ACTION和和GOTO可按可按如下方法构造:如下方法构造:若项目若项目Ab属于属

52、于Ik,GO(Ik,a)= Ij,a为终结符,置为终结符,置ACTIONk,a为为“把状态把状态j和符号和符号a移进栈移进栈”,简记为,简记为“sj”;若项目若项目A属于属于Ik,那么,对任何非终结符,那么,对任何非终结符a,aFOLLOW(A),置,置ACTIONk,a为为“用产生式用产生式A进行归约进行归约”,简记为,简记为“rj”;其中,假定;其中,假定A为文法为文法G的第的第j个产生式个产生式若项目若项目SS属于属于Ik,则置,则置ACTIONk,#为可为可“接受接受”,简记为,简记为“acc”;若若GO(Ik, A)= Ij,A为非终结符,则置为非终结符,则置GOTOk, A=j;分

53、析表中凡不能用规则分析表中凡不能用规则1至至4填入信息的空白格均填上填入信息的空白格均填上“出错标出错标志志”。 语法分析器的初始状态是包含语法分析器的初始状态是包含S S的项目集合的状态的项目集合的状态SLRSLR分析举例分析举例文法文法G:(0) S E(1) E E+T (2) E T (3) T T*F(4) T F(5) F (E)(6) F iI0:S E E E+T E T T T*F T F F (E) F iI1:S E E E+TI2:E T T T*FI3:T FI4:F (E) E E+T E T T T*F T F F (E) F iI5:F iI6:E E+T T

54、T*F T F F (E) F iI7:T T*F F (E) F iI8:F (E) E E+TI9:E E+T T T*FI11:F (E)I10:T T*FFOLLOW(S)#FOLLOW(E)#, ), +SLRSLR分析举例分析举例I1:S E E E+TI2:E T T T*FI9:E E+T T T*FFOLLOW(S)#FOLLOW(E)#, ), +状状态态ACTIONGOTOi+*()#ETF0s5s41231s6acc2r2s7r2r23r4r4r4r44s5s48235r6r6r6r66s5s4937s5s4108s6s119r1s7r1r110r3r3r3r311r5

55、r5r5r5构造规范构造规范LRLR语法分析表语法分析表SLRSLR文法中可能出现的冲突文法中可能出现的冲突文法文法G:(0) S S(1) S L=R(2) S R (3) L *R (4) L i(5) R LI0:S S S L=R S R L *R L i R LI1:S SI2:S L=R R LI3:S RI4:L *R R L L *R L iI5:L iI6:S L=R R L L *R L iI7:L *RI8:R LI9:S L=RSLRSLR语法分析的局限性语法分析的局限性所有的所有的SLR语法必须满足如下条件语法必须满足如下条件I = X b , A , B 若有:若有

56、:FOLLOW(A) FOLLOW(B) = FOLLOW(A) b = FOLLOW(B) b = 状态状态I面临某输入符号面临某输入符号a1) 若若a=b,则移进,则移进2) 若若a FOLLOW(A), 则用产生式则用产生式 A 进行归约进行归约3) 若若a FOLLOW(B), 则用产生式则用产生式 B 进行归约进行归约4) 此外,报错此外,报错构造规范构造规范LRLR语法分析表语法分析表针对针对SLR语法分析的局限性,我们给出如下解决方案:语法分析的局限性,我们给出如下解决方案:重新定义项目,使之包含一个终结符作为第二个分量,可以把更重新定义项目,使之包含一个终结符作为第二个分量,可

57、以把更多的信息并入状态中。多的信息并入状态中。项目的一般形式也就变成了项目的一般形式也就变成了A, a1a2ak ,其中,其中ALR(0)项目,每一个项目,每一个a都是终结符或者都是终结符或者#。LR(k)项目中的项目中的a1a2ak称为它的向前搜索符串(或展望串)称为它的向前搜索符串(或展望串)搜索符对搜索符对是非空的产生式没有什么影响是非空的产生式没有什么影响这样的这样的a的集合是的集合是FOLLOW(A)的子集,有可能是真子集的子集,有可能是真子集归约项目归约项目A, a1a2ak意味着:当它所属的状态呈现在栈顶意味着:当它所属的状态呈现在栈顶且后续的且后续的k个输入符号为个输入符号为a

58、1a2ak时,才可以把栈顶的时,才可以把栈顶的归约为归约为A。我们只对我们只对k1的情形感兴趣的情形感兴趣 LR(1)LR(1)LR(1)对活前缀有效的定义对活前缀有效的定义形式的,形式的,LR(1)的项目的项目A, a对活前缀对活前缀有效,如果存在推有效,如果存在推导导S=*A=,其中:,其中:=a是是的第一个符号,或者的第一个符号,或者是空串,是空串,a是是#。对于对于Closure运算的新定义运算的新定义考虑对考虑对对活前缀对活前缀有效的项目集中的项目有效的项目集中的项目AB,a必定存在一必定存在一个最右推导个最右推导S=*Aax=Bax,其中,其中=。假设假设ax能推导出终结符串能推导

59、出终结符串by,那么对每一个形如,那么对每一个形如B的产生的产生式,存在推导式,存在推导S=*Bby =by ,于是,于是B, b对对有效有效可以说,可以说,b是是FIRST(ax)中的任何终结符,根据中的任何终结符,根据FIRST的定义,的定义, FIRST(ax)= FIRST(a)。规范规范LRLR语法分析表的构造语法分析表的构造步骤步骤构造拓广文法构造拓广文法G的的LR(1)项目集规范族项目集规范族C=I0,I1,In从从Ii构造语法分析器的状态构造语法分析器的状态i,状态,状态i的分析动作如下:的分析动作如下:如果如果Aa, b在在Ii中,且中,且goto(Ii,a)= Ij,则置,

60、则置actioni,a为为sj ,即,即“移动移动j进栈进栈”,这里要求,这里要求a必须是终结符必须是终结符如果如果A, a在在Ii中,且中,且A$,则置,则置actioni,a为为rj ,即按照,即按照rj归约,归约,其中其中j是产生式是产生式A的序号的序号如果如果SS, $在在Ii中,则置中,则置actioni,$为为acc,表示接受,表示接受如果上述出现冲突,那么该文法不是如果上述出现冲突,那么该文法不是LR(1)文法文法状态状态i的转移按照下面的方法确定:如果的转移按照下面的方法确定:如果goto(Ii,A)= Ij,那么那么gotoi,a=j其余表项设为出错其余表项设为出错初始状态是

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论