编译原理作业集第七章
编译原理 第7章习题解答

第七章习题解答7.1 给定文法:S→(A)A→ABBA→BB→bB→c①构造它的基本LR(0)项目集;②构造它的LR(0)项目集规范族;③构造识别该文法活前缀的DFA;④该文法是SLR文法吗?若是,构造它的SLR分析表。
7.2 给定文法:E→EE+E→EE*E→a①构造它的LR(0)项目集规范族;②它是SLR(1)文法吗?若是,构造它的SLR(1)分析表;③它是LR(1)文法吗?若是,构造它的LR(1)分析表;④它是LALR(1)文法吗?若是,构造它的LALR分析表。
7.3 给出一个非LR(0)文法。
7.4 给出一个SLR(1)文法,但它不是LR(0)文法,构造它的SLR分析表。
7.5 给出一个LR(1)文法,但它不是LALR(1)文法,构造它的规范LR(1)分析表。
7.6 给定二义性文法:① E→E+E② E→E*E③ E→(E)④ E→id用所述的无二义性规则和(或)另加一些无二义性规则,例如,给算符*、+施加某种结合规则。
①构造它的LR(0)项目集规范族及识别活前缀的DFA;②构造它的LR分析表。
习题参考答案7.1 解:文法的基本LR(0)项目集为S→.(A) S→(.A) S→(A.) S→(A).A→.ABB A→A.BB A→AB.B A→ABB.A→.B A→B. B→.b B→b.B→.c B→c.构造该文法的识别活前缀的DFSA如下图所示:I文法的识别活前缀的DFSA该文法的LR(0)项目集规范族={I0,I1,I2,I3,I4,I5,I6,I7,I8}因为在构造出来的识别活前缀的DFA中,每一个状态对应的项目集都不含有移进-归约、归约-归约冲突,所以该文法是LR(0)文法,当然也是SLR文法。
因为 FOLLOW(S)={#}FOLLOW(A)=FIRST{)}∪FIRST(BB)={),b,c}FOLLOW(B)=FIRST(B)∪FOLLOW(A)={b,c,)}其对应的SLR(1)分析表如下表所示。
编译原理第七章

例题
设有文法G(L)
LE,L LE Ea Eb
文法G(L)的LR分析表如下
ACTION表
状态 0 1 2 3 4 5 S3 S4 S5 r3 r4 a S3 b S4 acc r2 r3 r4 2 6 , # E 2
GOTO表
L 1
6
r1
以输入串“a,b,a”为例,给出LR分析 器的分析过程如下表示:
步骤 1 2 3 4 5 0 03 02 025 0254 状态栈 # #a #E #E, #E,b 符号栈 输入符号串 分析动作 a,b,a# S3(移进) ,b,a# r3(规约) ,b,a# S5(移进) b,a# S4(移进) ,a# r4(规约)
6
7 8 9
0252
02525 025253 025252
S4
S6 r2 r2 S8 r3 r3 r3 r2
3
7
r4 r1
r4 r1
r4 r1
以输入串“abbcde”为例,给出LR分析器的分析过程如下表示:
步骤 1 2 3 4 5 6 7 8 9 0 02 024 023 0236 023 0235 02358 02357 状态栈 # #a #ab #aA #aAb #aA #aAc #aAcd #aAcdB 符号栈 输入符号串 分析动作
7.1.2 分析表或分析函数
LR分析表是LR分析器的核心。 分析表由两个子表构成,即动作表(ACTION表)和状 态转换表(GOTO表)。它们都是二维数组形式(数组 名称分别是GOTO和ACTION)。
对于GOTO表。它的一个数组元素GOTO(Sm,Xi)代表一 个状态。表示当状态Sm面临输入符号Xi时转移到的下一个状态 (通常Xi是非终结符)。 对于ACTION表。它的一个数组元素ACTION(Sm, ai)代表一 个动作,表示当状态Sm面临输入符号ai时完成的分析动作(通 常ai是终结符)。动作可以有四种可能,分别是移进、规约、 接受和出错。
编译原理Chapter 7

prev
next 40
LR(0)分析表的构造※
dir
LR(0)分析表相当于识别活前缀的有限自动
机DAF的状态转换矩阵
prev
next 41
LR(0)分析表的构造算法
dir
令包含S’→•S 的项目集Ik的下标k为分析器的初态
LR(0)分析表的ACTION和GOTO表的构造步骤如下:
若项目 A→•a 属于Ik,且转换函数GO(Ik,a)= Ij ,当a为终结符时,则置ACTION[k,a]为Sj 若项目 A→• 属于Ik ,则对a为任何终结符或‘#’, 置ACTION[k,a] = rj ,j为产生式在文法G’中的编 号 若项目 X→•A 属于Ik ,且GO(Ik,A)= Ij ,则置 GOTO[k,A]=j,其中A为非终结符,j为某一状态号 若项目 S’→S• 属于Ik ,则置ACTION[k,#] = acc 其它填上“报错标志”,可用空白表示
Step2 对初态集或其它所构造的项目集应用转
换函数 GO(I,X)= CLOSURE(J)求出新状态 J的项目集
Step3 重复Step2直到不出现新的项目集为止
prev next 36
dir
S’ E A B
E aA | bB cA | d cB | d
c
c a
I4:Ac•A A•cA A•d I2:Ea•A A•cA A•d
prev
next 46
S’E[0] EaA[1]|bB[2] AcA[3]|d[4] BcB[5]|d[6]
dir
对输入串bccd#的分析
符号栈 输入串 bccd# ACTION S3
up
步骤 状态栈 0 1 03 2 035 3 0355 4 5 6 7
编译原理第7章(刘磊 机械工业出版社)

语法制导方法的分类: 语法制导方法的分类: (1)自顶向下语法制导:以LL(1)分析为基础 )自顶向下语法制导: 分析为基础 (2)自底向上语法制导:以LR (1)分析为基础 )自底向上语法制导: 分析为基础
LL(1)文法: LL(1)文法: 文法 G: S → A B A → a A|b B → b B|c 的动作文法: G的动作文法: S → #Init# A B A → a A|b #Add # B → b #Add# B|c #Out_Val#
7.3 类型检查和类型转换
把类型检查的工作放在中间代码生成时 进行。 进行。
类型检查类型和类型检查的语法单位
类型相容性检查项目
各种条件表达式的类型是否是布尔类型 运算符的运算分量是否相容 赋值语句的左、 赋值语句的左、右部类型是否相容 实参与形参的类型是否相容 下标表达式的类型是否为所允许的类型 函数说明中的函数类型与返回值的类型是 否一致
类型检查的语 法单位
if语句、while语 if语句、while语 语句 repeat语句 句、repeat语句 表达式 赋值语句 过程调用语句、 过程调用语句、 函数调用语句 下标变量 赋值语句
7.4 中间代码生成中的几个问题
语义信息的获取与保存 语义栈sem sem及其操作 语义栈sem及其操作 常用的语义子程序 1.申请临时单元 1.申请临时单元 2.存放中间代码的子程序 存放中间代码的子程序Generate 2.存放中间代码的子程序Generate 3.产生一条中间代码子程序GenCode。 产生一条中间代码子程序GenCode 3.产生一条中间代码子程序GenCode。
7.1.2ቤተ መጻሕፍቲ ባይዱ抽象语法树和有向无环图
抽象语法树: 抽象语法树: Abstract Grammer 有向无环图: 有向无环图: Directed Acyclic 设有c:=a*b+a*b, c:=a*b+a*b,对应的 设有c:=a*b+a*b,对应的 AGT 和
北方工业大学编译原理第7章习题

7.8 请给出
if A and B and C > D then
if A <B then F:=1
else F:=0
else G:=G+1; 的四元式序列,翻译过程中,采用then 与else 的最近匹配原则。
解:100 ( jnz , A , _ , 102 ) /* A and B and C>D */ 101 ( j , _ , _ , 112 ) 102 ( jnz , B , _ , 104) 103 ( j , _ , _ , 112 ) 104 ( j> , C , D , 106 ) 105 ( j , _ , _ , 112 ) 106 ( j< , A , B , 108 ) /* A < B */ 107 ( j , _ , _ , 110 ) 108 ( := , 1 , _ , F ) /* F:=1 */ 109 ( j , _ , _ ,0) 110 ( := , 0 , _ , F ) /* F:=0 */ 111 ( j , _ , _ , 109) 112 (+ , G , 1 , T1 ) 113 ( := , T1 , _ , G )
TToo EE11.ftarluse
E2.code
TToo EE.truuee To E.false
103 (j,_,_,0) /*为假*/
104 105 106
(jnz,C,_,103) (j,_,_,106) (jnz,D,_,104)
/*为假*/ /*假链链首*/
(1) E→E1 or M E2 { backpatch(E1.falselist,
编译原理第七章例题

编译原理第七章例题1.写出下列表达式的三地址形式的中间表示。
(1)5+6 ? (a + b);(2)?A∨( B ∧ (C ∨ D));(3)for j:=1 to 10 do a[j + j]:=0;(4)if x > y then x:=10 else x:= x + y;答:⑴100: t1:=a+b101: t2:=6*t1102: t3:=5+t2⑵100: if A goto 102101: goto T102: if B goto 104103: goto F104: if C goto T105: goto 106106: if D goto T107: goto F⑶100: j:=1101: if j>10 goto NEXT102: i:=j+j103: a[i]:=0104: goto 101⑷100: if x>y goto 102101: goto 104102: x:=10103: goto 105104: x:=x+y105:2.将语句if A V B>0 then while C>0 do C:=C+D翻译成四元式。
答:100 (jnz,A,-,104)101 (j,-,-,102)102 (j>,B,0,104)103 (j,-,-,109)104 (j>,C,0,106)105 (j,-,-,109)106 (+,C,D,T1)107 (:=,T1,-,C)108 (j,-,-,104)1093.试将下述程序段翻译成三地址形式的中间代码表示。
while ( a+b<="" a="b" bdsfid="102" or="" p=""> while ( a<5 AND b<10 ){ a=a+1;b=b+1;}答:三地址代码如下:100: t:=a+b101: if t<="" bdsfid="110" goto="" p="">102: goto 103103: if a=b goto 105104: goto 112105: if a<5 goto 107106: goto 100107: if b<10 goto 109108: goto 100109: a:=a+1110: b:=b+1111: goto 105112:4.While a>0 ∨b<0doBeginX:=X+1;if a>0 then a:=a-1else b:=b+1End;翻译成四元式序列。
编译原理第7章答案

第七章LR分析法1.已知文法A→aAd|aAb|ε判断该文法是否是SLR(1)文法,若是构造相应分析表,并对输入串ab#给出分析过程。
解:增加一个非终结符S/后,产生原文法的增广文法有:S/→AA→aAd|aAb|ε下面构造它的LR(0)项目集规范族为:02对于I0来说有FOLLOW(A)∩{a}={b,d,#}∩{a}=Φ所以在I0状态下面临输入符号为a时移进,为b,d,#时归约,为其他时报错。
对于I2来说有也有与I0完全相同的结论。
这就是说,以上的移进-归约冲突是可以解决的,因此该文法是SLR(1)文法。
其他SLR(1)分析表为:下面构造它的SLR(1)项目集规范族为:15S→a|^|(T)T→T,S|S(1)构造它的LR(0),LALR(1),LR(1)分析表。
(2)给出对输入符号串(a#和(a,a#的分析过程。
(3)说明(1)中三种分析表发现错误的时刻和输入串的出错位置有何区别。
解:(1)加入非终结符S/,方法的增广文法为:S/→SS→aS→^S→(T)T→T,ST→S下面构造它的LR(0)项目集规范族为:表7.15.1 文法的LR(0)分析表17.若包含条件语句的语句文法可缩写为:S→iSeS|iS|S;S|a其中:i代表if,e代表else,a代表某一语句。
若规定:(1)else与其左边最近的if结合(2);服从左结合试给出文法中i,e,; 的优先关系,然后构造出无二义性的LR分析表,并对输入串iiaea#给出分析过程。
解:加入S/→S产生式构造出增广文法如下:[0] S/→S[1] S→iSeS[2] S→iS[3] S→S;S[4] S→a由习惯可知,定义文法中i,e,;,a4个算符的优先关系为:a>e>i>;。
并且i与;的结合方向均为自左至右。
由上述状态项目集可见:a.状态I1存在移进-归约冲突,由于FOLLOW(S/)∩{;}={#}∩{;}=Φ,所以面临#号时应acc,面临;号时应移进。
编译原理作业集-第七章(精选.)

编译原理作业集-第七章(精选.)第七章语义分析和中间代码产⽣本章要点1. 中间语⾔,各种常见中间语⾔形式;2. 说明语句、赋值语句、布尔表达式、控制语句等的翻译;3. 过程调⽤的处理;4. 类型检查;本章⽬标掌握和理解中间语⾔,各种常见中间语⾔形式;各种语句到中间语⾔的翻译;以及类型检查等内容。
本章重点1.中间代码的⼏种形式,它们之间的相互转换:四元式、三元式、逆波兰表⽰;3.赋值语句、算术表达式、布尔表达式的翻译及其中间代码格式;4.各种控制流语句的翻译及其中间代码格式;5.过程调⽤的中间代码格式;6.类型检查;本章难点1. 各种语句的翻译;2. 类型系统和类型检查;作业题⼀、单项选择题:1. 布尔表达式计算时可以采⽤某种优化措施,⽐如A and B⽤if-then-else可解释为_______。
a. if A then true else B;b. if A then B else false;c. if A then false else true;d. if A then true else false;2. 为了便于优化处理,三地址代码可以表⽰成________。
a. 三元式b. 四元式c. 后缀式d. 间接三元式3. 使⽤三元式是为了________:a. 便于代码优化处理b. 避免把临时变量填⼊符号表c. 节省存储代码的空间d. 提⾼访问代码的速度4. 表达式-a+b*(-c+d)的逆波兰式是________。
a. ab+-cd+-*;b. a-b+c-d+*;c. a-b+c-d+*;d. a-bc-d+*+;5. 赋值语句x:=-(a+b)/(c-d)-(a+b*c)的逆波兰式表⽰是_______。
a. xab+cd-/-bc*a+-:=;a. xab+/cd-bc*a+--:=;a. xab+-cd-/abc*+-:=;a. xab+cd-/abc*+--:=;6. 在⼀棵语法树中结点的继承属性和综合属性之间的相互依赖关系可以由________来描述。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
第七章语义分析和中间代码产生本章要点1. 中间语言,各种常见中间语言形式;2. 说明语句、赋值语句、布尔表达式、控制语句等的翻译;3. 过程调用的处理;4. 类型检查;本章目标掌握和理解中间语言,各种常见中间语言形式;各种语句到中间语言的翻译;以及类型检查等内容。
本章重点1.中间代码的几种形式,它们之间的相互转换:四元式、三元式、逆波兰表示;3.赋值语句、算术表达式、布尔表达式的翻译及其中间代码格式;4.各种控制流语句的翻译及其中间代码格式;5.过程调用的中间代码格式;6.类型检查;本章难点1. 各种语句的翻译;2. 类型系统和类型检查;作业题一、单项选择题:1. 布尔表达式计算时可以采用某种优化措施,比如A and B用if-then-else可解释为_______。
a. if A then true else B;b. if A then B else false;c. if A then false else true;d. if A then true else false;2. 为了便于优化处理,三地址代码可以表示成________。
a. 三元式b. 四元式c. 后缀式d. 间接三元式3. 使用三元式是为了________:a. 便于代码优化处理b. 避免把临时变量填入符号表c. 节省存储代码的空间d. 提高访问代码的速度4. 表达式-a+b*(-c+d)的逆波兰式是________。
a. ab+-cd+-*;b. a-b+c-d+*;c. a-b+c-d+*;d. a-bc-d+*+;5. 赋值语句x:=-(a+b)/(c-d)-(a+b*c)的逆波兰式表示是_______。
a. xab+cd-/-bc*a+-:=;a. xab+/cd-bc*a+--:=;a. xab+-cd-/abc*+-:=;a. xab+cd-/abc*+--:=;6. 在一棵语法树中结点的继承属性和综合属性之间的相互依赖关系可以由________来描述。
a. 抽象语法树;b. 语法规则;c. 依赖图;d. 三地址代码;7. 按照教材中的约定,三地址语句if x relop y then L表示成四元式为。
a. (relop,x,y,L);b. (relop,L,x,y);c. (relop,x,L,y);d. (L,x,y,relop);8. 在编译程序中,不是常见的中间语言形式。
a.波兰式;b. 三元式;c. 四元式;d. 抽象语法树;9. 在编译程序中安排中间代码生成的目的是________。
a. 便于提高编译效率;b. 便于提高分析的正确性;c. 便于代码优化和目标程序的移植;d.便于提高编译速度;10. 按照教材中的约定,下面不是类型表达式:a. boolean;b. type-error;c. real;d. DAG;11. 一个Pascal函数function f ( a, b:char ) :↑integer;……其作用域类型是:a. char×integer;b. char×char;c. char×pointer(integer);d. integer×integer;12. 因为标识符可用于多种情况,比如常量标识符、变量标识符、过程标识符等等。
因此,在符号表中为了给出各个符号的标志,常给标识符引入一个属性kind,然后在相应产生式的语义动作中添加给kind属性赋值的语句。
比如,在在产生式D id:T的语义动作中添加赋值语句id.kind=。
a. V AR;b. CONSTANT;c. PROC;d. FUNC;13. 下面情况下,编译器需要创建一张新的符号表。
a. 过程调用语句;b. 标号说明语句;c. 数组说明语句;d.记录说明语句;14. 函数function f(a,b:char):↑integer;…所以f函数的类型表达式为:a. char×char→pointer(integer);b. char×char→pointer;c. char×char→integer;d. char×char→integer (pointer)15. 如果一个语言的编译器能保证编译通过的程序,在运行时不会出现类型错误,则称该语言是。
a. 静态的;b. 强类型的;c. 动态的;d. 良类型的;一.答案:1. b;2. d;3. b;4. d;5. c;6. c.;7. a;8. a;9. c;10. d;11. b;12. a;13. d;14. a;15. b;二、填空题:1. 语法分析是依据语言的语法规则进行的,中间代码产生是依据语言的________规则进行的。
2. 多目运算x:=y[i]的三元式表示为两部分:________________和________________。
3.生成三地址代码时,临时变量的名字对应抽象语法树的____________。
4. 一个类型表达式或者是基本类型,或者由____________施加于其它类型表达式组成。
5. 在程序设计语言中,布尔表达式有两个基本的作用:一个是;另一个是。
6. 允许嵌套过程的语言,其过程说明语句的翻译用两个栈tblptr和offset分别保存尚未处理完的过程的和它们的offset,这两个栈顶的元素分别是正在处理的过程的的符号表指针和。
7. 在一些pascal的实现中,如果说明中出现了没有名字的类型表达式,编译器这样处理:建立一个来和每个声明的变量标识符相联系。
8. 赋值语句a:=b*-c+b*-c的后缀式为。
9. 多目运算X[i]:=y的三元式表示为两部分:________________和________________。
10. 编译器遇到常量说明时,要把常量值登录入并回送序号;在中为等号左边的标识符建立新条目,在该条目中填入常量标志、相应类型和常量表序号。
11.典型的转移条件语句:if E then S1 else S2中,作为转移条件的布尔表达式E,赋予它两种“出口”:一是;二是。
12. 类型表达式或者是,或者是作用在其它类型表达式上得到的新的类型表达式。
13. pascal变量说明:var A:array[1..10] of integer与A相关的类型表达式为:。
14.若T是类型表达式,则pointer(T)是类型表达式,它表示类型。
15.通过一遍扫描来产生布尔表达式和控制流语句的代码存在一个问题,就是当生成某些转移语句时可能还不知道该语句将要转移到的语句的地址是什么。
采用的办法来解决这个问题。
二.1. 语义;2. (0): ( [ ]=, y, i ),(1): ( assign, x, (0) );3. 内部结点;4. 类型构造符;5. 计算逻辑值;作控制流语句中的条件表达式;6. 符号表指针,相对地址;7. 隐含的类型名;8. a b c uminus * b c uminus * + assign;9.(0):(=[ ],x,i);(1):(assign,(0),y);10. 常量表;符号表;11. “真”出口,转向S1;“假”出口,转向S2;12. 基本类型;类型构造符;13. array(1..10, integer) ;14. “指向T类型对象的指针”;15. “拉链-回填”三、判断题:1. 中间代码是独立于机器的,复杂性介于源语言和机器语言之间,便于进行与机器无关调换代码优化工作。
()2. 在程序设计语言中,一般来说,布尔表达式仅仅用于条件、循环等控制流语句中的条件表达式计算。
()3. “回填”技术用于对过程中的说明语句进行处理时把计算出的有关符号的属性填入符号表。
( )4. 如果E是一个常量或变量,则E的逆波兰式是E自身。
( )5. 对于任何一个编译程序来说,中间代码的产生是不一定必要的。
()6. 由于三元式中的三个域中,仅有两个域与地址有关,所以,三元式不是严格意义上的三地址代码。
()7. 两个类型表达式要么是同样的基本类型,要么是同样的类型构造符作用于结构等价的类型,我们就说,这两个类型系统等价。
()8. 对于Pascal这样允许嵌套过程的语言,每当遇到过程说明D→proc id ; D1; S时,便创建一张新的符号表,也就是说,让每个过程说明都有自己一张独立的符号表。
()9. 记录类型的各个域变量分配存储区域的地址的确定是相对于为记录类型变量所分配存储区域的首地址的,所以记录类型不应该建立自己的符号表。
()10. 类型表达式中不可出现类型变量,即类型变量值不是类型表达式。
()11. 所谓类型系统就是把类型表达式赋给语言各相关结构成分的规则的集合。
同一种语言(比如C++语言)的编译程序,在不同的实现系统里(比如微软的Visual C++和Linux下的开源编译器TCC),可能使用不同的类型系统。
12. 四元式表示的是四地址代码,三元式表示的是三地址代码。
()13. 生成三地址代码时,临时变量的名字对应抽象语法树的内部结点。
()14. 后缀式是抽象语法树的线性表示形式,后缀式是树结点的一个序列,其中每个结点都是在所有子结点之后立即出现的。
()15. 后缀表示形式只是用于表达式的,其他的语法结构比如条件语句、循环语句等不能使用后缀式。
()三.答案:1. √;2. ×;3. ×;4. √;5. √;6. ×;7. √;8. √;9. ×;10. ×;11. √;12. ×;13. √;14. √;15. ×;四、名词解释:1. 三地址代码;2. 回填;3. 类型表达式;4. 类型系统;5. 静态语义检查四.答案:1. 三地址代码是由下面一般形式的语句构成的序列:x:= y op z。
其中x、y、z为名字、常数或编译时产生的临时变量;op代表运算符号如定点运算符、浮点运算符、逻辑运算符等等,每个语句的右边只能有一个运算符。
2. 通过一遍扫描来产生布尔表达式和控制流语句的代码的主要问题在于,当生成某些转移语句时我们可能还不知道该语句将要转移到的标号是什么。
为了解决这个问题,可以在生成形成分支的跳转指令时,暂时不确定跳转目标,而建立一个链表,把转向这个目标的跳转指令的标号键入这个链表,一旦目标确定之后再把它填入有关的跳转指令中。
这种技术称为回填。
3. 一个类型表达式或者是基本类型,或者由类型构造符施于其他类型表达式组成。
基本类型和类型构造符都因具体语言的不同而不同。
Ⅰ. 一个基本类型是一个类型表达式。
Ⅱ. 类型名是一个类型表达式Ⅲ. 类型构造符作用于类型表达式,其结果仍然是类型表达式Ⅳ. 类型表达式中可出现类型变量,即变量值是类型表达式。