pl/0编译程序的研究与改进

pl/0编译程序的研究与改进

摘要:为了加深对编译原理理论的理解,同时熟练掌握编译技术的应用,引入了pl/0语言编译机制。在掌握pl/0文法体系后,通过跟踪pl/0语言编译程序的的具体转化过程,我们对编译原理中如词法分析、语法分析,中间代码生成,错误处理等过程进行了具体的研究,同时在此基础上,对pl/0文法进行了进一步的拓展与改进。
关键词:PL/0语言;编译机制;编译原理;语法拓展;
前言:编译原理课程是计算机科学与技术专业本科生的必修课,该系列课程用于逐渐提高计算机科学与技术学科所要求学生具有的使用计算机进行问题求解、软件设计及实现等基本能力。本课程以形式语言为理论基础,通过对编译理论和技术的讲授,向学生介绍软件系统设计和基本方法。通过对本课程的学习,除了掌握词法分析、语法分析、语法制导翻译和存储分配、代码优化等基本方法外,同时了解和初步掌握“理论—抽象—设计—实现”制作软件的4个过程,以达到自觉应用的目的。本文引入了PL/0语言编译程序,通过跟踪实例程序被编译的过程,深入理解编译技术的基本原理和实现方法。在此基础上,我们有自行在源代码的基础上,为PL/0 编译程序机制增添了“+=”、“-=”、“*=”、“/=”、“++”、“–”、“for循环”、“”等功能。

1 PL/0语言基本知识
1.1PL/0语言文法体系
1:〈程序〉::=〈分程序〉.
2:〈分程序〉::= 〈[ 常量说明部分〉]〈[ 变量说明部分〉]〈[ 过 程说明部分〉〈] 语句〉
3:〈常量说明部分〉::=CONST〈常量定义〉{,〈常量定义〉};
4:〈常量定义〉::=〈标识符〉=〈无符号整数〉
5:〈无符号整数〉::=〈数字〉{〈数字〉}
6:〈变量说明部分〉::=VAR〈标识符〉{,〈标识符〉};
7:〈标识符〉::=〈字母〉{〈字母〉〈| 数字〉}
8:〈过程说明部分〉::=〈过程首部〉〈分程序〉{;〈过程说明 部分〉};
9:〈过程首部〉::=PROCEDURE〈标识符〉;
10:〈语句〉::=〈赋值语句〉〈| 条件语句〉〈| 当型循环语句〉| 〈过程调用语句〉〈| 读语句〉〈| 写语句〉〈| 复合语句〉〈| 空〉
11:〈赋值语句〉::=〈标识符〉:=〈表达式〉
12:〈复合语句〉::=BEGIN〈语句〉{;〈语句〉}END
13:〈条件〉::=〈表达式〉〈关系运算符〉〈表达式〉|ODD〈表 达式〉
14:〈表达式〉::= [+|-〈] 项〉{〈加法运算符〉〈项〉}
15:〈项〉::=〈因子〉{〈乘法运算符〉〈因子〉}
16:〈因子〉::=〈标识符〉〈| 无符号整数〉‘|(’〈表达式〉‘)’
17:〈加法运算符〉::= + | -
18:〈乘法运算符〉::= * | /
19:〈关系运算符〉::= = | # |< | <= | > | >=
20:〈条件语句〉::=IF〈条件〉THEN〈语句〉
21:〈过程调用语句〉::=CALL〈标识符〉
22:〈当型循环语句〉::=WHILE〈条件〉DO〈语句〉
23:〈读语句〉::=READ‘(’〈标识符〉{,〈标识符〉‘} )’
24:〈写语句〉::=WRITE‘(’〈表达式〉{,〈表达式〉‘} )’
25:〈字母〉::= a | b | … | X | Y | Z 26:〈数字〉::=0 | 1 | 2 | … | 8 | 9
1.2 PL/0语言结构框架
PL/0 语言编译程序仅由 17 个过程和 2 个函数构成。
PL0编译程序过程与函数(与代码编程实现对应)
1.3 PL/0程序示例
var d,i,b;
procedure p;
begin
for i:=0; to b; do;
d:=i+d;
if d<=55
then
write(d)
else
begin
d:=0;
d++;d–;
d+=1;d-=1;
d/=1;d*=1;
write(d);
end
end;
begin
d:=0;
read(b);
while b>0 do
begin
call p;
end
end.
在接下去PL/0编译程序执行时,会将此PL/0程序转化成P-code虚拟机代码。
2 PL/0语言的编译过程
2.1 构建编译各阶段所需的信息表
在 PL/0 语言编译程序中,主过程 pl0 首先建立 4 个数组 类型的变量 word、wsym、ssym、mnemonic 和 3 个集合类型的变 量 declbegsys、statbegsys、facbegsys,它们的任务就是存储编译 过程中需要使用的各种信息。其功能简介如下所示。
word:存储 PL/0 语言的 13 个保留字;
wsym:与 word 数组一起判别各保留字的类别;
ssym:用于识别 PL/0 语言中的各种符号(如+、-、*、/等);
mnemonic:存储PL/0 语言中 8 条目标指令的助记符,用于 输出目标代码;
declbegsys、statbegsys、facbegsys:根据相应文法,判断所处 的语法结构。 这 7 个变量构成了编译过程中必需的“信息字典”。
2.2 词法分析的实现原理
PL/0编译程序主过程执行时调用getsym读入源程序的第一个有效单词。
涉及到有效单词时,我们把有效单词分为五大类:保留字,用户自定义的标识符,常数,运算符,界符。getsym 过程的实质就是完成编译过程中的词法分析工 作。它每被调用一次,就从源程序文件中读入一些字符,直到 识别出一个单词为止,并判断其各种属性,包括类别、层次、值 等,然后存入相应的全局变量中,便于在后续的编译过程中使用。在调用getsym过程后,便完成了识别有效单词的功能,具体实现过程是通过调用负责完成这个功能的代码实现的。
2.3 语法语义分析的实现原理和技术
对于一个上下文无关文法 G =(VT,VN,S,P),在对其定义的语言 L(G)进行分析的时候, 选择哪一个产生式往下推导的前提是需要知道每个产生式的 开始符号集是什么。开始符号集的定义如下:
FIRST( )={ * , , , *}
因此,可以计算 FIRST(常量声明)={const}
FIRST(变量声明)={var}
FIRST(过程声明)={procedure}
FIRST(语句)={ident,begin,call,if,while,read,write}
并且,上下文无关文法要求各非终结符的开始符号集不 相交,即FIRST(常量声明)∩FIRST(变量声明)∩FIRST(过程声 明)∩FIRST(语句)= ∅。
对于常亮,变量,过程声明的处理时,用语法分析过程block调用getsym读入程序语句。对于常量,用记录型数组table记录常量名称、类型、值;对于变量,在table表中记录变量名、类别、变量声明所在的层次和地址;对于过程声明,开始时将过程名、类别、层次、该过程数据区所占的大小录入table,在编译程序执行完全部程序的语法分析工作之后,利用回填技术填入该过程的地址信息。
2.4 目标代码生成的实现原理和技术
目标代码生成要做的就是调用目标代码生成过程产生于源代码功能等价的目标代码。生成目标代码的工作主要由statement过程完成该过程通过反复使用if…then…else控制语句,将对各种句型的处理转入相应的分支流程中。
以赋值语句为例,构成形式为“<标识符>:=<表达式>”,因此,statement过程首先判断第一个单词是否为用户自定义的标识符。如果不是,则退出判断分支,测试下一句型分支,若是,这的调用position过程查找本标识符在table数组中的位置。如果找到,则返回标识符地址,并检查是否为变量类型,若不是,则抛出错误;若是,则判断紧跟标识符的单词是否为赋值值符号“:=”,若不是,则抛出错误;若是,则调用expression过程处理出现在“:=”左边的表达式。如果 expression 过程执行完毕并且没有发 生任何错误,statement过程就产生一条 STO 指令,将存放在栈 顶的表达式的结果发送到“:=”左边的变量中。
接下来用factor过程首先判断读入的单词是数还是标识符,然后再根据单词的类型产生相应的指令。其代码如下:
with table[i] do
case kind of
constant: gen(lit , 0 , val)(; * 若标识符为常量,则产生一 条将其取至栈顶的指令 *)
variable: gen(lod , lev-level , adr)(; * 若标识符为变量,则 产生一条将该变量取至栈顶的指令 *)
procedure: error(21)(; * 如果出现在“:=”右部的是一个过 程名,则抛出 21 号错误,指出在表达式内,标识符属性不能是 过程 *)
end;
由以上factor过程处理,可以即可生成目标代码。最后,编译程序读入代表程序结束的“.”。如果代码生成 过程没有出现任何错误,pl0 主过程就调用 interpret 过程解释 执行生成的目标代码。这
2.5 错误处理原理和技术
错误处理过程发生在词法分析、语法分析和目标代码生成过程中,若所读入的代码符号类型与预期读入的不符,则抛出错误。在以上词法分析语法分析和目标代码生成小节已具体讲述。
3 PL/0语言的拓展

  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值