版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、程设计班级 学号 姓名21301马瑞泽百度一. 课程设计目的在分析理解一个教学型编译程序(如 PL/0 )的基础上,对其词法分析程序、语法分 析程序和语义处理程序进行部分修改扩充。达到进一步了解程序编译过程的基本原理和基 本实现方法的目的。二. 课程设计要求1. 基本内容(1 )扩充赋值运算:+=和-=(2) 扩充语句(Pascal的FOF语句): FOR 变量 := 表达式 TO 表达式 DO 语句 FOR 变量 := 表达式 DOWNTO表达式 DO 语句其中,语句的循环变量的步长为 2,语句的循环变量的步长为-2。2. 选做内容(1) 增加运算:+和-。(2) 增加类型: 字符类型; 实
2、数类型。(3) 扩充函数: 有返回值和返回语句; 有参数函数。(4) 增加一维数组类型(可增加指令)。(5) 其他典型语言设施。3. 本人在课程设计中已实现的功能(1) 增加单词:保留字 ELSE, FOR TQ DOWNTO, REPEAT, UNTIL, RETURN运算符+=+(3) 增加条件语句的ELSE子句(4) 扩充赋值运算:+=和-=(5) 扩充语句 FOR 变量 :=表达式 TO 表达式 DO 语句 FOR 变量 :=表达式 DOWNTO表达式 DO 语句(6) 增加运算:+和-(包括前后+、-运算)(7) 增加一维数组类型(8) 其他典型语言设施:REPEAT语句UNTIL语
3、句三. 课程设计环境与工具(1) 计算机及操作系统:PC机,Win7(2) 实现工具:VC+ 6.0, C语言(3) 教学型编译程序:PL/0四. 结构设计说明1) PL/0编译程序的结构图2) PL/0编译程序的过程或函数的功能表置初值启动过程或函数名简要功能说明pio主程序error出错处理,打印出错位置和错误编码getsym词法分析,读取一个单词getch漏掉空格,读取一个字符gen生成目标代码,并送入目标程序区test测试当前单词符号是否合法block分程序分析处理过程en ter登录名字表positi on(函数)查找标识符在名字表中的位置con stdeclarati on常量定义
4、处理vardeclarati on变量说明处理listode列出目标代码清单stateme nt语句处理expressi on表达式处理term项处理factor因子处理con diti on条件处理in terpret对目标代码的解释执行程序base(函数)通过静态链求出数据区的基地址3) PL/0编译程序的总体流程图4)词法分析词法分析是编译的第一个阶段,它的主要任务是从左向右逐个字符地对源程序进行扫 描,产生一个个单词序列用于语法分析。PL/O词法分析程序GETSY的功能是为语法分析 提供单词用的,是语法分析的基础,把输入的字符串形式的源程序分割成一个个单词符号。 经过词法分析程序分析出
5、来的单词,对语言固有的单词只给出类别存放在全程变量 SYM中, 而对用户定义的单词(标识符或常数)既给出类别又给值,其类别放在SYM中,值放在全程变量ID或全程变量NUM中,全部单词种类由编译程序定义的纯量类型SYMBOLS出,称为语法词汇表。词法分析器的分析过程:调用 GETSY时,它通过GETCH过程从源程序中获得一个字 符。如果这个字符是字母,则继续获取字符或数字,最终可以拼成一个单词,查保留字表, 如果查到为保留字,则把SYM变量赋成相应的保留字类型值;如果没有查到,则这个单词 应是一个用户自定义的标识符(可能是变量名、常量名或是过程的名字),把SYMS为IDENT 把这个单词存入ID
6、变量。查保留字表时使用了二分法查找以提高效率。如果Getch获得的字符是数字,则继续用 Getch获取数字,并把它们拼成一个整数或实数,然后把SYMS为INTEGER并把拼成的数值放入NUM变量。如果识别出其它合法的符号(比如:赋值号、 大于号、小于等于号等),则把SYM则成相应的类型。如果遇到不合法的字符,把 SYM置 成NUL词法分析程序GETSY将完成下列任务:(1)滤空格(2)识别保留字(3)识别标识符(4)拼数(5)拼复合词(6)输出源程序5)语法分析PL/0编译程序的语法分析采用了自顶向下的递归的子程 序法。语法分析同时也根据程序的语义生成相应三元代码, 并提供了出错处理的机制。语
7、法分析主要由分程序分析过程(BLOC) 常量定义分析过程(ConstDeclaration )、变量定 义分析过程(Vardeclaration )、语句分析过程(Statement )、 表达式处理过程(Expression )、项处理过程(Term)、因子 处理过程(Factor、和条件处理过程(Condition、构成。这 些过程在结构上构成一个嵌套的层次结构。除此之外,还有 出错报告过程(Error )、代码生成过程(Gen)、测试单词合 法性及出错恢复过程(Test )、登录名字表过程(Enter )、查 询名字表函数(Position、以及列出类PCODE代码过程(Listcode
8、、作过语法分析的辅助过程。由PL/0的语法图可知:一个完整的 PL/0程序是由分程 序和句号构成的。因此,本编译程序在运行的时候,通过主 程序中调用分程序处理过程 block来分析分程序部分(分程 序分析过程中还可能会递归调用block过程),然后,判断最后读入的符号是否为句号。如果是句号且分程序分析中未出 错,则是一个合法的PL/0程序,可以运行生成的代码,否则 就说明源PL/0程序是不合法的,输出出错提示即可。6)语义分析PL/0的语义分析主要进行以下检查:(1)是否存在标识符先引用未声明的情况;(2)是否存在己声明的标识符的错误引用;程序7分 程f语句1r条件1F表达项1r土子一PL/0
9、语法调用关系(3)是否存在一般标识符的多重声明。7) 中间代码生成目标代码类 pcode是一种假想栈式计算机的汇编语言。自己添加覆盖了OPR 0 14栈顶值输出至屏幕(字符型)OPR 0 15栈顶值输出至屏幕(整数型)OPR 0 16栈顶值输出至屏幕(实数型)OPR 0 17屏幕输出换行OPR 0 18从命令行读入一个字符输入置于栈顶OPR 0 19从命令行读入一个整数输入置于栈顶OPR 0 20从命令行读入一个实数输入置于栈顶8) 语法错误处理PL/0 编译程序对语法错误的处理采用两种办法:(1)对于一些易于校正的错误,如丢了逗号、分号等,指出出错的位置,加以校正, 继续进行分析。(2)对于
10、难于校正的错误,给出错误的位置与性质,跳过后面一些单词,直到下一 个可以进行正常语法分析的语法单位。错误类型如下0 过程开始部分说明不正确1 常数说明中 = 写成 :=2 常数说明中 = 后应为整数或实数或字符3 常数说明中的标识符后应是 =4 const, var, procedure 后应为标识符5 漏掉了 , 或 ;6 过程说明后的符号不正确 (应该是语句开始符 , 或过程定义符 )7 应是语句开始符8 程序体内语句部分的后跟符不正确9 程序结尾丢了句号 .10 语句间漏了 ;11 标识符未说明12 赋值语句中 , 赋值号左部标识符属性应是变量13 变量后不能是此符号14 call 后应
11、为标识符15 call 后标识符属性应为过程16 条件语句中丢了 then17 丢了 end或;18 while 型循环语句丢了 do19 语句后的符号不正确20应为关系运算符21表达式内标识符属性不能是过程22表达式中漏掉右括号(23因子后的非法符号24表达式的开始符不能是此符号31数越界补充说明了:32 read 或 write语句括号中的标识符不是变量33 read 或 write34 read 或 write35 read 或 write语句缺少右括号) 语句缺少左括号( 括号里应为变量自己增加了:45 +或-后面应为变量46 repeat 缺少 until47 for语句错误48 f
12、or语句缺少do49类型值不匹配50类型无法转换51只有整数能+或-52类型不正确TEST测试过程流程图五. 设计过程(一)实验内容1. 增加单词:保留字 ELSE, FOR, TO, DOWNTO, REPEAT, UNTIL, RETURN运算符 +=(PLUSBK), -=(MINUSBK), +(INC), - (DEC)首先要扩展SYMBQL在此基础上再进行其它细节的修改。要添加的SYMBO为:typedef enum NUL, IDENT, NUMBER, PLUS, MINUS, TIMES,SLASH, ODDSYM, EQL, NEQ, LSS, LEQ, GTR, GEQ,
13、LPAREN, RPAREN, COMMA, SEMICOLON, PERIOD, BECOMES, BEGINSYM, ENDSYM, IFSYM, THENSYM, WHILESYM, WRITESYM, READSYM, DOSYM, CALLSYM, CONSTSYM, VARSYM, PROCSYM, PROGSYM, ELSESYM,FORSYM, TOSYM, DOWNTOSYM, REPEATSYM, UNTILSYM, RETURNSYM, PLUSBK, MINUSBK, INC, DEC SYMBOL;char *SYMOUT = NUL, IDENT, NUMBER,
14、PLUS, MINUS, TIMES, SLASH, ODDSYM, EQL, NEQ, LSS, LEQ, GTR, GEQ, LPAREN, RPAREN, COMMA, SEMICOLON, PERIOD, BECOMES, BEGINSYM, ENDSYM, IFSYM, THENSYM, WHILESYM, WRITESYM, READSYM, DOSYM, CALLSYM, CONSTSYM, VARSYM, PROCSYM, PROGSYM, ELSE,FOR,TO, DOWNTO, REPEAT, UNTIL, RETU RN, PLUSBK, MINUSBK, INC ” D
15、EC ;其中黑斜体为新加入的SY MBQL再将 ELSE,FOR,TO,DOWNTO, REPEAT,UNTIL, RETURN,PLUSBK, MINUSBK, INC,DEC关键字加到KWOR和将相应的SYM加到WSYM按字母顺序排列。以及修改NEQ后如下void _fastcall TForm1:ButtonRunClick(TObject *Sender) for (CH= ; CHv=a: ch+) SSYMCH=NUL;strcpy(KWORD 1,BEGIN); strcpy(KWORD 2,CALL); strcpy(KWORD 3,CONST); strcpy(KWORD 4
16、,DEC);strcpy(KWORD 5,DO); strcpy(KWORD 6, DOWHILE); strcpy(KWORD 7, DOWNTO ); strcpy(KWORD 8,ELSE);strcpy(KWORD 9,END); strcpy(KWORD 10,FOR); strcpy(KWORD 11,IF); strcpy(KWORD12,INC); strcpy(KWORD13,MINUSBK); strcpy(KWORD14,ODD); strcpy(KWORD15,PLUSBK); strcpy(KWORD16,PROCEDURE); strcpy(KWORD17,PROG
17、RAM); strcpy(KWORD18,READ); strcpy(KWORD19,REPEAT); strcpy(KWORD20,RETURN); strcpy(KWORD21,THEN); strcpy(KWORD22,TO); strcpy(KWORD23,VAR); strcpy(KWORD24,UNTIL);strcpy(KWORD25,WHILE); strcpy(KWORD26,WRITE);WSYM 1=BEGINSYM; WSYM 2=CALLSYM;WSYM 3=CONSTSYM; WSYM 4=DEC;WSYM 5=DOSYM; WSYM 6=DOWHILESYM;WS
18、YM 7=DOWNTOSYMs; WSYM 8=ELSESYM;WSYM 9=ENDSYM; WSYM 10=FORSYM;WSYM 11=IFSYM; WSYM12=INCSYM;WSYM13=MINUSBK; WSYM14=ODDSYM;WSYM15=PLUSBK; WSYM16=PROCSYM;WSYM17=PROGSYM; WSYM18=READSYM;WSYM19=REPEATSYM; WSYM20=RETURNSYM;WSYM21=THENSYM; WSYM 22=TOSYM;WSYM23=VARSYM; WSYM24=UNTILSYM;WSYM25=WHILESYM; WSYM2
19、6=WRITESYM;SSYM+=PLUS; SSYM-=MINUS;SSYM*=TIMES; SSYM/=SLASH;SSYM(=LPAREN; SSYM)=RPAREN;SSYM=EQL; SSYM,=COMMA;SSYM.=PERIOD; SSYM;=SEMICOLON;因为关键字增加到了 26 个,所以令 const NORW = 26;SYMBO由原来的33个值扩展为目前的44个值,SYMOU也由原来的33个元素扩展 为目前的44个元素.我用个SYMMA来记录SYMBO值的个数, 所以,除了 Error 函数中可能出现的作为参数的“3 3”不被替换为“4 4”外,其余的“3 3”均用
20、“ SYMMAX来替换。SY MBO扩展完毕。2. 修改单词:不等号 # 改为 只要修改GetSym()函数。当编译器检测到当前字符为“”时,接着检测下一个字符,如果是“”,则使SYM二NEQ代码修改如下:if (CH=) SYM=NEQ; GetCh (); /增加 为不等于号;else SYM=LSS;3. 增加条件语句的ELSE子句该条件语法描述图如下:语句只要在STATEMENT修改如下代码:case IFSYM:GetSym();CONDITION(SymSetUnion(SymSetNew(THENSYM,DOSYM),FSYS),LEV,TX);if (SYM=THENSYM)
21、GetSym();else Error(16);CX1=CX; GEN(JPC,O,O);STATEMENT(SymSetUnion(SymSetNew(ELSESYM), FSYS), LEV, TX);if(SYM != ELSESYM) C0DECX1.A=CX;/如果程序中没有else语句,执行JPC时跳到此地址else /添加ELSE语句GetSym();CX2=CX;GEN(JMP,O,O); /跳过 else 语句CODECX1.A = CX;/如果程序中有else语句,执行JPC时跳到此地址STATEMENT(FSYS ,L EV,TX);C0DECX2.A = CX; /执行
22、完then语句后跳出break;ELSE子句扩充完毕。(二)课程设计内容1.增加运算符+=,-=,+,-a) 词法分析1)在GetSym()中完成INC( + + )、PLUSBK( + =)的词法分析,代码修改如下:else if(CH = +)GetCh();if(CH = =)/增加 +=SYM = PLUSBK;GetCh();else if(CH = +)/增加 +SYM = INC;GetCh();else SYM = PLUS;2)在GetSym()中完成 DEC( )、MINUSBR =)的词法分析,代码修改如下:else if(CH = -)GetCh();if(CH = =
23、)/增加 -=SYM = MINUSBK;GetCh();else if(CH = -)/增加 -SYM = DEC;GetCh(); else SYM = MINUS;b) 扩充后+和后-操作存在 INC 和 DEC 操作的语法图有如下两个:根据以上语法图,我们只要对语句处理程序和因子处理程序进行修改添加,即可实现增加 后INC和 后DEC操作,首先对语句处理程序STATEMEN进行如下修改:Case IDENT:i=POSITION (ID,TX);if (i=0) Error(11);elseif (TABLEi.KIND!=VARIABLE) /*ASSIGNMENT TO NON-V
24、ARIABLE*/ Error(12); i=0;GetSym();if (SYM=BECOMES)GetSym ();EXPRESSION (FSYS, LEV, TX);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);else if (SYM=INC) /语句中的 +运算 if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN(LIT,0,1);GEN(OPR,0,2);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);
25、GetSym();else if (SYM=DEC) /语句中的 - 运算 if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN (LIT,0,1);GEN (OPR,0,3);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym ();在接受到SYM=IDEN后,如果SYM为INC,则主要执行这四条指令:GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR)将IDENT的值放到栈顶,GEN(LIT,0,1); 将常数 1 放到栈顶,GEN
26、(OPR,0,2) 次栈顶加栈顶,GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);将栈顶内容保存到IDENT中。这样就完成了语句中的 +运算。如果SYM为DEC则主要执行这四条指令:GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR)将IDENT的值放到栈顶,GEN(LIT,0,1); 将常数 1 放到栈顶,GEN(OPR,0,3) 次栈顶减栈顶,GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);将栈顶内容保存到IDENT中。这样就完成了语句中的 - 运算。其次,再对因子处理程序 FACT
27、O修改如下:if (SYM=IDENT) i=POSITION(ID,TX); if (i=0) Error(11); else switch (TABLEi.KIND) case CONSTANT: GEN(LIT,0,TABLEi.VAL);GetSym(); break; case VARIABLE: GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); GetSym();if(SYM=INC|SYM=DEC) / GEN(LIT,0,1);因子中的 +和- 运算if(SYM=INC) GEN(OPR,0,2);如果为 INC,则加 1else GEN(
28、OPR,0,3);否则减一将栈顶送入变量单元将变量送入栈顶GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); / GetSym();break;case PROCEDUR: Error(21); break;这样,对后INC和后DEC操作就扩充完成c)扩充前+和前-操作存在 前INC和前DEC操作的语法图有如下两个:首先将STATBEGSYSINC=1;STATBEGSYSDEC=1;FACBEGSYSINC =1;FACBEGSYSDEC =1;其次根据以上语法图,我们只
29、要对语句处理程序和因子处理程序进行修改添加,即可实现增加前INC和前DEC操作,首先对语句处理程序STATEMEN进行如下修改:case INC:/前+GetSym();if (SYM = IDENT) i=POSITION(ID,TX);if (i=0) Error(11);else if (TABLEi.KIND!=VARIABLE) /*ASSIGNMENT TO NON-VARIABLE*/Error(12); i=0;if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN(LIT,0,1);GEN(OPR,0,2);if (i
30、!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym();else Error(45);break;case DEC: /前-GetSym();if (SYM = IDENT) i=POSITION(ID,TX);if (i=0) Error(11);else if (TABLEi.KIND!=VARIABLE) /*ASSIGNMENT TO NON-VARIABLE*/Error(12); i=0;if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN (LIT,0,1);GE
31、N (OPR,0,3);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym ();else Error(45);break;再次,再对因子处理程序 FACTO修改如下:else if(SYM = INC) /前 +GetSym();if (SYM = IDENT) i=POSITION(ID,TX);if (i=0) Error(11);else if (TABLEi.KIND!=VARIABLE) /*ASSIGNMENT TO NON-VARIABLE*/ Error(12); i=0;if (i!=0) GEN(LOD,
32、LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN(LIT,0,1);GEN(OPR,0,2);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); /将栈顶送入变量单元GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); /将变量送入栈顶GetSym();else Error(45);else if(SYM = DEC) /前 -GetSym();if (SYM = IDENT) i=POSITION(ID,TX);if (i=0) Error(11);else if (TABL
33、Ei.KIND!=VARIABLE) /*ASSIGNMENT TO NON-VARIABLE*/Error(12); i=0;if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN (LIT,0,1);GEN (OPR,0,3);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); /将栈顶送入变量单元GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR); /将变量送入栈顶GetSym ();else Error(45);d) 扩充+=和-=操作这两
34、个操作都是一种对变量进行赋值的形式,其合法的语句形式的语法图如下所示:根据图3,在语句处理STATEMENT,在已经处理INC和DEC勺基础上,添加对PLUSBK(+ =)运算和 MINUSBIK =)运算的扩充,相关代码添加如下:else if (SYM=PLUSBK) / 增加运算符 +=if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym();EXPRESSION(FSYS,LEV,TX);GEN(OPR,0,2);if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);e
35、lse if (SYM=MINUSBK) /增加运算符 -=if (i!=0) GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym();EXPRESSION(FSYS,LEV,TX);GEN(OPR,0,3); if (i!=0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);这样就完成了对+=运算和=运算的添加。2. 增加Pascal的FOR语句:a) 格式如下:FOR 变量 := 常数TO(或 DOWNTO)常数 DO 语句b) 添加语句for 语句的语句语法图如下:首先 ,词法分析部分增加关键字在 S
36、YMBO里增加 FORSYM, TOSYM, DOWNTQSYM应 SYMMAX=44 ; NORW = 25;初始化中strcpy(KWORD10,FOR); WSYM 10=IFSYM;strcpy(KWORD22,TO);WSYM22=TOSYM;strcpy(KWORD 7,DOWNTO); WSYM 7=DOWNTOSYM;其次,修改STATEMENT代码如下:case FORSYM: / 添加 FOR语句。GetSym();if(SYM != IDENT) Error(47);else i=POSITION(ID,TX);if(i = 0) Error(11);else if (T
37、ABLEi.KIND!=VARIABLE) /*ASSIGNMENT TO NON-VARIABLE*/Error(12); i=0;GetSym();if(SYM = BECOMES) GetSym();else Error(13);EXPRESSION(SymSetUnion(SymSetNew(TOSYM,DOWNTOSYM),FSYS),LEV,TX);if(i != 0) GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);if(SYM = TOSYM) / 如果是 to 语句CX1=CX;/ 记录当前地址入口GEN(LOD,LEV-TABLEi.v
38、p.LEVEL,TABLEi.vp.ADR);/ 取 ident 变量值到栈顶GetSym();EXPRESSION(SymSetUnion(SymSetNew(DOSYM),FSYS),LEV,TX);/ 取表达式值到栈顶GEN(OPR,0,13);/ 判断变量是否小于或等于栈顶CX2=CX;GEN(JPC,0,0);GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GEN(LIT,0,1);GEN(OPR,0,2);GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);/ 变量加一if(SYM = DOSYM)/执行DO后
39、的语句GetSym();STATEMENT(FSYS,LEV,TX);else Error(48);GEN(JMP,0,CX1);CODECX2.A=CX;else if (SYM=DOWNTOSYM) /如果为 down语句CX1=CX;GEN(LOD,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);GetSym();EXPRESSION(SymSetUnion(SymSetNew(DOSYM),FSYS),LEV,TX);GEN(OPR,0,11);/变量大于或等于栈顶CX2=CX;GEN(JPC,0,0);GEN(LOD,LEV-TABLEi.vp.LEVEL,TA
40、BLEi.vp.ADR);GEN(LIT,0,1);GEN(OPR,0,3);GEN(STO,LEV-TABLEi.vp.LEVEL,TABLEi.vp.ADR);/ 变量减一if (SYM=DOSYM)执行DO后的语句GetSym();STATEMENT(FSYS,LEV,TX);else Error(48);GEN(JMP,0,CX1); CODECX2.A=CX;else Error(47);break; II添加FOF语句。FOF语句扩充完毕。3. 增加一维数组类型 首先设置一维数组的左右括号: ssym=lepa;II一维数组的左括号 ssym=ripa;II一维数组的右括号 根据栈
41、顶的偏移地址从数组中取值到新根据次栈顶的偏移地址把栈顶的值存入将栈顶的值下移到次栈顶,栈顶出栈,即出栈顶判断数组下标合法性将数组的下标范围入栈, gendo(tra,0, 数增加指令: strcpy(&(mnemonicgar0),gar); II 的栈顶 strcpy(&(mnemonicsar0),sar);II 数组 strcpy(&(mnemonicshd0),shd);II 次栈顶成为栈顶 strcpy(&(mnemonicdel0),del);II strcpy(&(mnemonicjud0),jud);II strcpy(&(mnemonictra0),tra);II 组下标最大
42、值 );增加标识符类型属性:/*- 标识符的类型属性 -*/enum objectconstant,variable,procedur,array, / 数组;在 block ()函数中添加如下代码: for(i=tx0+1;iamax)error(31);num=0;table(*ptx).val=num;break;case variable: /*table(*ptx).level=lev;table(*ptx).adr=(*pdx);table(*ptx).size=0;(*pdx)+;break; /*case procedur:table(*ptx).level=lev;break
43、;case array: /*table(*ptx).level=lev;table(*ptx).adr=(*pdx)-arraysize; table(*ptx).size=arraysize; break;变量名字 */过程名字 */数组名字 */在 Vardeclaration ()函数中添加数组的变量声明,代码如下: int vardeclaration(int * ptx,int lev,int * pdx)int i;char idtempal+1;/ 临时保存数组名字if(sym=ident)strcpy(idtemp,id);getsymdo;/ 如果是数组if(sym=lepa)/ 数组的左中括号getsymdo;if(sym=number)/a 中的中括号里是数字的话*pdx=*pdx+num;/ 为数组分配空间 arraysize=num;/ 保存数组的长度else中的中括号里是变量的话if(sym=ident)/a查找名字表/ 要检查是不是以声明的常量i=position(id,*ptx);/if(i=0)error(11);/ 标识符未说明else标识符的属性是常量为数组分配空间保存数组的长度if(tablei.kind=constant)/*pdx=*pdx+tablei.val;/arraysize
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- (2024版)市场营销合作与客户数据保护协议
- 员工食品安全
- 体育服装采购与营销方案
- 物业管理安全服务方案
- 2024年光伏发电项目投资开发合同
- 2024年化工场地租赁合同
- 制造业企业战略咨询合同
- 2024年仲裁调解合同的服务内容
- 2024年国际快递物流服务协议
- 2024年加工承揽合同样本
- 2024年河南省信阳市招才引智绿色通道招聘市直事业单位人员183人高频难、易错点500题模拟试题附带答案详解
- XXXX酒店管理公司成立方案
- 民用无人机操控员执照(CAAC)考试复习重点题及答案
- 2024年中国南水北调集团水网水务投资限公司及下属单位社会招聘高频难、易错点500题模拟试题附带答案详解
- 广西南宁市第十四中学2023-2024学年七年级上学期期中地理试题
- 2024-2030年中国应急产业市场发展分析及竞争形势与投资机会研究报告
- 2024年中国电动鼻毛器市场调查研究报告
- 2024年中国具身智能行业研究:知行合一拥抱AI新范式-19正式版
- 数字中国发展报告(2023年)
- 缺乳(乳汁淤积)产妇的中医护理
- 《理解与尊重》主题班会
评论
0/150
提交评论