编译原理实验一(3)——for循环
注:
课程:《编译技术》上机
实验一:词法语法分析器的设计与实现,生成抽象语法树。
建议使用词法语法分析程序生成工具如:LEX/FLEX , YACC/BISON等专业工具完成。
此处完成补充 for循环 的操作
前期准备
- 已完成上一篇文章中的补充char操作
- 已经将整个文件夹都备好份,以供魔改后的回溯
开始实验
第一步
修改lex.l文件(lex描述文件给出了每一类词法单元的规则)
- 第37行插入对字符串for的识别
- 第38行插入对字符串break的识别
- 第39行插入对字符串continue的识别
第二步
修改parser.y文件(parser.y是C语言文法)
- 第36行插入单词声名FOR BREAK CONTINUE
- 修改Stmt第92行插入for的语句
解释一下Stmt指代是语句,for循环整体算作一个语句在这里定义FOR LP Def Exp SEMI Exp RP Stmt(对照着for(int a=0;a<10;a++){printf(" %d ",a);}来看) LP是左括号, Def是变量定义语句,因为Def包含分号;,所以下一个直接接上了Exp Exp是复合表达式/语句(不带分号;) SEMI是分号 又来一个EXP,a++可以看做是一个复合表达式的 Rp是右括号 Stmt,我想用的是Stmt:Compst这个文法, Compst是函数体,有大括号包起来的变量定义列表+语句列表
{$$=mknode(4,FOR,yylineno,$3,$4,$6,$8);}的含义 mknode是创建子节点的函数, 4表示创建4个节点 FOR是该文法的标识(type) yylineno是当前行数 $3,$4,$6,$8分别对应Def Exp Exp Stmt(几个非终结符)
- 第125-126行插入break,continue的文法
终结符不用创建子节点,所以mknode的第一个参数为0
第三步
修改ast.c文件(ast.c定义了树的生成与输出)
- 在第83行插入for的输出
感觉不需要解释,每一个语句都是顺其自然的
先输出For循环声名,这是父节点,然后子节点有四个,每个都indent+3
而indent+6是子节点的内部定义,是子节点的子节点
- 第93行插入break,contiue的输出
补:解释一下 printf("% * cCHAR:%c\n",indent,’ ‘,T->type_char);的含义:先打印indent个空格,再打印CHAR:%c
默认低一级的话,往后移3个空格
第四步
修改test.c文件(测试代码)
- 第16-19行是测试for循环
- 第18行是测试break
- 第25是测试continue
结果检验
依次运行
flex lex.l
bison -d parser.y
gcc -o parser lex.yy.c parser.tab.c ast.c
parser test.c
发现有乱码,使用chcp 65001切换到UTF-8编码界面
for循环输出完成!
break输出完成!
continue输出完成!
for循环补充完成啦!有没有感觉自己又会了hhhhhh
写在结尾
希望以上可以帮到你!
如有错误,或不同想法,欢迎指出,互相学习共同进步!
Share this content:
发表评论