大三上学期做的一个小项目

类C编译器

源代码和测试文件地址https://github.com/zxt1995/ttbox.git

总体框架: 读入待编译文件->语义分析并转换为指令->按照指令进行栈操作->得出结果

拓展部分(个人负责内容 其他内容在代码中有注释)

完成内容

Do while循环

Switch case语句

Goto语句

循环中Break和continue的实现

补充基础部分的短路计算

词法分析(switch)

Switch语句加入关键字 SYM_SWITCH,SYM_CASE,SYM_DEFAULT ,SYM_BREAK

加入新的OPR操作 OPR_CMP 保留栈顶和次栈顶 次栈顶是switch后面的选择表达式的结果值 栈顶为1(相等) 0(不相等)

语法分析(switch)

switch(expression)

begin

Case num1:

为0跳转 Statement(若最后无break);

Case num2:   JMP到下一个Statement开头

为0跳转 Statement(若最后有break);

Case num3:

为0跳转 Statement;

Default:   JMP到结束

Statement;

end;

代码分析(switch)

在pl0.h中加入全局变量

在statement中 加入

Switch语句正常检测对应SYM 然后做一次表达式计算即可

在switch语句的最后

要判断是否出现default来给最后一个case决定跳转位置

Case部分代码如下 default类似

Break 等待回填

截图示例(switch)

测试样例如下

左边是测试代码 右边是步骤

下面是结果 结果只计算了一开始i的赋值和p=30  j=40满足switch的语法规则

(这里结果是每次参数赋值之后的结果 后面的测试结果类同,组内其他成员实现了print函数可以输出特定的参数结果)

词法分析(goto)

加入关键字SYM_GOTO

加入新的label(字符型2元数组)

语法分析(goto)

begin:

statement

jmp statement

goto: label1;

Statement

label2:

statement

Statement jmp

goto: label2;

statement

label1:

statement

end;

只要匹配到对应的label就无条件跳转就可以

但是由于不知道对应的label是在哪里出现 所以要在block结束后再回填跳转指令

代码分析(goto)

首先在statement的if(getsym()==SYM_IDENTI)中加入无法辨别的id将他判别为标识符

然后在statement的if(getsym()==SYM_GOTO)中存入另一个label

最后在main函数的block之后进行字符串匹配就行

截图示例(goto)

测试样例如下

结果满足goto语法

词法分析(do while)

Statement中重写SYM_DO

语法分析(do while)

do

Statement 为0跳转

while(expression);

代码分析(do while)

基本实现方式和while循环类似

截图示例(do while)

(见continue break 和do while共同示例)

词法分析(break continue)

加入关键字 SYM_BREAK

SYM_CONTINUE

加入全局变量

每次进入循环的时候 loopfi++ 出循环的时候loopfi-- 这样就不会在回填时出现失误

(注回填指令在出循环之后马上回填)

语法分析(break continue)

以while循环为例(begin end总体归约为一个大的statement)

While(expression)

begin

Statement  无条件跳转到expression之前

Continue;

Statement

break;

Statement 无条件jmp到循环结束

Statement

End;

代码分析(break continue)

在do while语句 for循环语句 while循环语句中都有修改 以while语句为例

添加识别sym   Break和continue如下

截图示例(break continue )

附带do while

结果正确

词法分析(补充bool短路)

加入全局变量如下

加入和JPC相反的指令JNP不是0跳转

语法分析(补充bool短路)

先以一层为例

Expression简写为expi JNP到结束

JPC到同层第一个||之后

多层就存到对应层的的trur_list和false_list然后结束代表括号之后的位置即可

代码分析(补充bool短路)

如下以if语句为例

修改func_or和func_and基本同上

以or为例

遇到and更新假值链

遇到or更新真值链(同时填写同层与上一层的假值出口)

遇到Not交换真值假值链内容

示例截图

指令序列中不再出现opr_or 和opr_and

结果正确

总结(有什么能修改的地方)

Goto语句中label的数量

支持break continue的循环层数

Swich case中case和break的数量 都有一定上限!!

有待更好的数据结构来表述而不是二维/一维数组

所有代码https://github.com/zxt1995/ttbox.git

转载于:https://www.cnblogs.com/tokitoki/p/8536874.html

类C编译器 C代码实现相关推荐

  1. c++ 模板类实现堆栈实验报告_编译原理——小型类C编译器的设计和实现(生成8086汇编代码)之1:问题定义以及总体功能...

    前面花了两篇文章来介绍词法分析和语法分析,接下来才是比较有意思的部分--一个小型类C编译器的设计和实现(其实是编译原理的课程设计啦!~)我用的是python2.7.13+PyQt来做的...事实上,正 ...

  2. 基于虎书实现LALR(1)分析并生成GLSL编译器前端代码(C#)

    基于虎书实现LALR(1)分析并生成GLSL编译器前端代码(C#) 为了完美解析GLSL源码,获取其中的信息(都有哪些in/out/uniform等),我决定做个GLSL编译器的前端(以后简称编译器或 ...

  3. Java查漏补缺(08)关键字:static、单例设计模式、理解main方法、类的成员之四:代码块、final关键字、抽象类、接口、内部类、枚举类、注解、包装类

    Java查漏补缺(08)关键字:static.单例设计模式.理解main方法.类的成员之四:代码块.final关键字.抽象类.接口.内部类.枚举类.注解.包装类 本章专题与脉络 1. 关键字:stat ...

  4. Linux C++性能优化秘籍:从编译器到代码,探究高性能C++程序的实现之道

    Linux C++性能优化秘籍:从编译器到代码,揭秘高性能C++程序的实现之道 引言 性能优化的重要性 Linux环境下C++程序的特点 高性能C++编程的核心要点 编译器优化 GCC与Clang编译 ...

  5. 支持向量机python代码_用TensorFlow实现多类支持向量机的示例代码

    这篇文章主要介绍了用TensorFlow实现多类支持向量机的示例代码,现在分享给大家,也给大家做个参考.一起过来看看吧 本文将详细展示一个多类支持向量机分类器训练iris数据集来分类三种花. SVM算 ...

  6. python对数组排序代码实现_Python自定义类的数组排序实现代码

    首先把实现方法写出来,其实很简单,只需要一句代码即可: 复制代码 代码如下: productlist.sort(lambda p1, p2:cmp(p1.getPrice(), p2.getPrice ...

  7. java.util.zip 用法,Java压缩文件工具类ZipUtil使用方法代码示例

    本文实例通过Java的Zip输入输出流实现压缩和解压文件,前一部分代码实现获取文件路径,压缩文件名的更改等,具体如下: package com.utility.zip; import java.io. ...

  8. Android沉浸式状态栏工具类,一句代码轻松搞定

    Android沉浸式状态栏工具类,一句代码轻松搞定 博客原文及源码地址:http://jaeger.itscoder.com/android/2016/03/27/statusbar-util.htm ...

  9. __declspec(naked)是用来告诉编译器函数代码的汇编语言为自己的所写,不需要编译器添加任何汇编代码

    __declspec(naked)是用来告诉编译器函数代码的汇编语言为自己的所写,不需要编译器添加任何汇编代码 extern "C" void __declspec(naked) ...

最新文章

  1. 如何在FineUIMvc(ASP.NET MVC)视图中绑定多个模型?
  2. 视频插帧--Video Frame Interpolation via Adaptive Convolution
  3. WINCE基于AT050TN22屏的时序描述
  4. vs2010 引入cout,cin ,endl报错,不能识别
  5. Spring源码:BeanFactory
  6. Nginx 多进程连接请求/事件分发流程分析
  7. 论坛分页频繁更新帖子缓存_如何实现频繁更改内容的“可缓存”分页
  8. dubbo与zookeeper的关系
  9. vue 查看变量类型_Vue学习 开始走向VUE开发2---插值使用详解
  10. python元组_Python元组
  11. jsf tree组件_JSF文本组件–标签,文本字段,文本区域和密码
  12. 七日Python之路--第八天(一些琐碎)
  13. 阿里这份Java程序性能优化指南,让你的程序快上200%
  14. html 引入 icon 图标
  15. 系统架构设计师教程-学习-记录(26)系统开发基础知识-软件开发方法(2)软件开发模型
  16. 如何正确地在Spring Data JPA和Jackson中用上Java 8的时间相关API(即JSR 310也即java.time包下的众神器)...
  17. bp神经网络缺点及克服,bp神经网络存在的问题
  18. 沉睡者IT - 10个问题说清楚:什么是元宇宙?
  19. 验证码 图片无法刷新
  20. 最近很火的盲盒交友源码v1.1.5 带教程

热门文章

  1. 【CyberSecurityLearning 22】传输层协议分析(TCP/UDP)
  2. ubuntu终端显示乱码的解决
  3. 【❌❌深入浅出,九浅一深⭕⭕】《深入理解计算机系统》CSAPP
  4. 都2021年了,不会还有人连深度学习都不了解吧(五)-- 下采样篇
  5. DM368开发 -- 硬件认识
  6. 如何定义Java对象
  7. Android热修复技术原理详解(最新最全版本)
  8. Python之区块链简单记账本实现
  9. 从并发视角来看智能合约(下)【渡鸦论文系列】
  10. (原创)Android6.0亮屏流程之Keyguard Window绘制