[计算机软件及应用]第7章 LR分析
作业 P166 1. 2. 3. 文法G‘:(0)S’? S(1)S? rD (2)D? D,i(3)D? i ? i I0:S‘ → ? SS‘ → ?rD I2: S → r?DD → ?D,iD → ? i I3: S → rD ? D →D ?,i I4: D → i ? I5: D → D,?i I1: S‘ → S ? I6: D →D,i ? S r D , i 分析每个状态包含的项目集,不难发现在状态I3中含项目: S→rD· 为归约项目 D→D·,i为移进项目 也就是按S→rD·项目的动作认为用S→rD产生式进行归约的句柄已形成,不管当前的输入符号是什么,都应把rD归约成S。但是按D→D·,i项目当面临输入符号‘,’号时,应将‘,’号移入符号栈,状态转向I5。显然该文法不是LR(0)文法,也可在构造它的LR(0)分析表时发现这个问题。 状态 ACTION GOTO r , i # S D 0 S 2 ? ? ? 1 ? 1 ? ? ? acc ? ? 2 ? ? S 4 ? ? 3 3 r1 r1,S5 r1 r1 ? ? 4 r3 r3 r3 r3 ? ? 5 ? ? S6 ? ? ? 6 r2 r2 r2 r2 ? ? I3: S → rD ? D →D ?,i 向前查看一个符号,看其是否是S的后跟符号(FOLLOW(S)),若否则移进,是则归约。 SLR(1)分析表 一个LR(0)规范族中含有如下的项目集(状态)I,I={X→??b?,A→??,B→??}若有:FOLLOW(A)∩FOLLOW(B)= ?FOLLOW(A)∩{b}= ?FOLLOW(B)∩{b}= ? SLR(1)文法 1)若a=b,则移进。 2)若a?FOLLOW(A),则用产生式A→?进行归约。 3)若a?FOLLOW(B),则用产生式B→?进行归约。 4)此外,报错。 状态I面临某输入符号a 通常对于LR(0)规范族的一个项目集I中可能含有多个移进项目和多个归约项目,我们可假设项目集I(状态)中有m个移进项目: A1→α1·a1β1,A2→α2·a2β2…,Am→αm·amβm:,同时含有n个归约项目为:B1→γ1·,B2→γ2·,…,Bn→γn·。 只要集合{a1,a2,…,am}和FOLLOW(B1),FOLLOW(B2),…,FOLLOW(Bn)两两交集都为空,那么我们仍可用上述规则解决冲突,即考查当前输入符号决定动作。 1)若a∈{a1,a2…am},则移进。 2)若a∈FOLLOW(Bi),i=1,2…n,则用Bi→γi进行归约。 3)此外,报错。 如果对于一个文法的LR(0)项目集规范族的某些项目集或LR(0)分析表中所含有的动作冲突都能用上述方法解决, 则称这个文法是SLR(1)文法,所构造的分析表为SLR(1)分析表, 使用SLR(1)分析表的 分析器称为SLR(1)分析器。上述解决方法称为SLR(1)规则。 对所有非终结符都求出其FOLLOW集合,这样只有归约项目仅对面临输入符号包含在该归约项目左部非终结符的FOLLOW集合中,才采取用该产生式归约的动作。 改进的SLR(1)分析表的ACTION表和GOTO表的构造步骤: 改进的SLR(1)分析表 A)若项目A→??a?属于Ik,且转换函数GO(Ik,a)=Ij,当a为终结符时,则置ACTION[k,a]为Sj。 B)若项目A→??属于Ik,则对a为任何终结符或‘#’,且满足a?FOLLOW(A)时,置ACTION[k,a]=rj,j为产生式在文法G‘中的编号。 C)若GO(Ik,A)=Ij,则置GOTO[k,A]=j,其中A为非终结符,j为某一状态号。 D)若项目S′→S?属于Ik,则置ACTION[k,#]=acc。 E)其它填上“报错标志”。 状态 ACTION GOTO r , i # S D 0 S2 1 1 acc 2 S4 3 3 S5 r1 4 r3 r3 r3 r3 5 S6 6 r2 r2 r2 r2 仍有许多文法构造的LR(0)项目集规范族存在的动作冲突不能用SLR(1)方法解决。 一个LR(0)规范族中含有如下的项目集(状态)I。I={X→??b?,A→??,B→??}有:FOLLOW(A)∩ FOLLOW(B)≠ ?或 FOLLOW(A)∩{b}≠ ? 或 FOLLOW(B)∩
原创力文档

文档评论(0)