1. 扫描器设计与编程实现(扫描器的设计与实现)
  2. NFA确定化算法设计与编程实现(NFA确定化(选做))
  3. 递归下降分析器设计与实现(预测分析方法设计与实现)
  4. 算符优先分析法设计与实现(算符优先分析程序设计实现)

目录

一、实验目的

二、实验内容

三、实验过程与结果

实验代码

data.txt文件

代码运行截图

四、总结与体会


一、实验目的

通过设计、编制并调试一个具体的词法分析程序,加深对词法分析原理的理解。掌握在对程序设计语言源程序进行扫描过程中,将其分解为各类单词的词法分析方法。

理解词法分析在编译程序中的作用;加深对有穷自动机模型的理解;掌握词法分析程序的实现方法和技术。

二、实验内容

自定义一种程序设计语言,或者选择已有的一种高级语言,编制它的词法分析程序。词法分析程序的实现可以采用任何一种编程语言和编程工具。

设计词法分析程序,从输入的源程序中,识别出各个具有独立意义的单词,即关键字、标识符、常数、运算符、界符,并依次输出各个单词的内部编码及单词符号自身值(遇到错误时可显示“Error”,然后跳过错误部分继续显示)。

(软件、硬件)环境:

软件环境:Visual Studio Code、CodeBlocks 17.12 编写、调试并执行实验代码

硬件环境:“Windows 10教育版”计算机

三、实验过程与结果

修改课本P212表C.1,将其扩充为C语言的保留字表,如下所示:

char *rwtab[] = {"int", "long", "short", "float", "double", "char", "unsigned", "signed", "const", "void", "volatile", "enum", "struct", "union","if", "else", "goto", "switch", "case", "do", "while", "for", "continue", "break", "return", "default", "typedef","auto", "register", "extern", "static", "sizeof", "begin", "then", "end", "cout", "main", _KEY_WORD_END};

实验代码

参考P212附录C,编写源程序,实验代码如下所示:

/*需要的库和全局变量、函数及主程序*/
#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#define _KEY_WORD_END "waiting for your expanding"using namespace std;typedef struct //词的结构,二元组形式(单词种别,单词自身的值)
{int typenum; //单词种别char *word;
} WORD;
char input[255];
char token[255] = "";
int p_input; //指针
int p_token;
char ch;
char *rwtab[] = {"int", "long", "short", "float", "double", "char", "unsigned", "signed", "const", "void", "volatile", "enum", "struct", "union","if", "else", "goto", "switch", "case", "do", "while", "for", "continue", "break", "return", "default", "typedef","auto", "register", "extern", "static", "sizeof", "begin", "then", "end", "cout", "main", _KEY_WORD_END};
WORD *scanner(); //扫描
int main()
{int over = 1;WORD *oneword = new WORD;//实现从文件读取代码段cout << "read something from data.txt" << endl;FILE *fp;if ((fp = freopen("data.txt", "r", stdin)) == NULL){printf("Not found file!\n");return 0;}else{while ((scanf("%[^#]s", &input)) != EOF){p_input = 0;printf("your words:\n%s\n", input);while (over < 1000 && over != -1){oneword = scanner();if (oneword->typenum < 1000){if (oneword->typenum != 999)cout << "[  " << oneword->typenum << "\t" << oneword->word << "  ]" << endl;}over = oneword->typenum;}scanf("%[^#]s", input);}}return 0;
}
//从输入缓冲区读取一个字符到ch中
char m_getch()
{ch = input[p_input];p_input++; // p_input = p_input + 1;return (ch);
}
//去掉空白符号
void getbc()
{while (ch == ' ' || ch == 10){ch = input[p_input];p_input++; // p_input = p_input + 1;}
}
//拼接单词
void concat()
{token[p_token] = ch;p_token++; // p_token = p_token + 1;token[p_token] = '\0';
}
//判断是否字母
int letter()
{if (ch >= 'a' && ch <= 'z' || ch >= 'A' && ch <= 'Z')return 1;elsereturn 0;
}
//判断是否数字
int digit()
{if (ch >= '0' && ch <= '9')return 1;elsereturn 0;
}//检索关键字表格
int reserve()
{int i = 0;while (strcmp(rwtab[i], _KEY_WORD_END)){if (!strcmp(rwtab[i], token))return i + 1;i++;}return 10; // 如果不是关键字,则返回种别码10
}
//回退一个字符
void retract()
{p_input--; // p_input = p_input - 1;
}//词法扫描程序
WORD *scanner()
{WORD *myword = new WORD;myword->typenum = 10; // 初始值myword->word = "";p_token = 0; //单词缓冲区指针m_getch();getbc(); //去掉空白if (letter()) //判断读取到的首字母是字母{//如intwhile (letter() || digit()){concat(); //连接m_getch();}retract();                   //回退一个字符myword->typenum = reserve(); //判断是否为关键字,返回种别码myword->word = token;return (myword);}else if (digit()) //判断读取到的单词首字符是数字{while (digit()) //所有数字连接起来{concat();m_getch();}retract();//数字单词种别码统一为20,单词自身的值为数字本身myword->typenum = 20;myword->word = token;return (myword);}elseswitch (ch){case '=':m_getch(); //首字符为=,再读取下一个字符判断if (ch == '='){myword->typenum = 39;myword->word = "==";return (myword);}retract(); //读取到的下个字符不是=,则要回退,直接输出=myword->typenum = 21;myword->word = "=";return (myword);break;case '+':myword->typenum = 22;myword->word = "+";return (myword);break;case '-':myword->typenum = 23;myword->word = "-";return (myword);break;case '/':          //读取到该符号之后,要判断下一个字符是什么符号,判断是否为注释m_getch();     //首字符为/,再读取下一个字符判断if (ch == '*') // 说明读取到的是注释{m_getch();while (ch != '*'){m_getch(); //注释没结束之前一直读取注释,但不输出if (ch == '*'){m_getch();if (ch == '/') //注释结束{myword->typenum = 999;myword->word = "注释";return (myword);break;}}}}else{retract(); //读取到的下个字符不是*,即不是注释,则要回退,直接输出/myword->typenum = 25;myword->word = "/";return (myword);break;}case '*':myword->typenum = 24;myword->word = "*";return (myword);break;case '(':myword->typenum = 26;myword->word = "(";return (myword);break;case ')':myword->typenum = 27;myword->word = ")";return (myword);break;case '[':myword->typenum = 28;myword->word = "[";return (myword);break;case ']':myword->typenum = 29;myword->word = "]";return (myword);break;case '{':myword->typenum = 30;myword->word = "{";return (myword);break;case '}':myword->typenum = 31;myword->word = "}";return (myword);break;case ',':myword->typenum = 32;myword->word = ",";return (myword);break;case ':':m_getch();if (ch == '='){myword->typenum = 18;myword->word = ":=";return (myword);break;}else{retract();myword->typenum = 33;myword->word = ":";return (myword);break;}case ';':myword->typenum = 34;myword->word = ";";return (myword);break;case '>':m_getch();if (ch == '='){myword->typenum = 37;myword->word = ">=";return (myword);break;}retract();myword->typenum = 35;myword->word = ">";return (myword);break;case '<':m_getch();if (ch == '='){myword->typenum = 38;myword->word = "<=";return (myword);break;}else if (ch == '<'){myword->typenum = 42;myword->word = "<<";return (myword);break;}else{retract();myword->typenum = 36;myword->word = "<";return (myword);}case '!':m_getch();if (ch == '='){myword->typenum = 40;myword->word = "!=";return (myword);break;}retract();myword->typenum = -1;myword->word = "ERROR";return (myword);break;case ' " ':myword->typenum = 41;myword->word = " \" ";return (myword);break;case '\0':myword->typenum = 1000;myword->word = "OVER";return (myword);break;case '#':myword->typenum = 0;myword->word = "#";return (myword);break;default:myword->typenum = -1;myword->word = "ERROR";return (myword);break;}
}

data.txt文件

int main()
{int a = 1, b = 2;b / a;/*测试注释和除号*/b > a;cout << "lwx!!!" << endl;return 0;
}

data.txt 文件截图:

 

代码运行截图

词法分析器,实验运行截图:

四、总结与体会

此次实验,参照课本编写了扫描器的设计,并将其实现。实验过程中,遇到了诸多困难,但都一一解决,加深了我对课本概念的理解,收获甚多。

使用文件操作的方式,从data.txt文件中读入要分析的程序,C语言中的文件操作并不难以实现,使用文件操作可以提升用户的体验感。编程时,将各个基本功能用函数来实现,使得程序的条理性增强了;全局变量的使用也使得数据在函数间的传递更加方便。

本次实验结合书本上的理论知识,我进一步了解词法分析程序构造的一些细节。在实验中,发现了自身的许多不足,课下我会多加努力。

编译原理【实验1——扫描器的设计与实现】相关推荐

  1. c语言词法分析器实验原理,词法分析器的设计与实现 编译原理实验报告.doc

    词法分析器的设计与实现 编译原理实验报告 中北大学软件学院 实 验 报 告 专 业 软件工程 课程名称 编译原理 学 号 姓 名 辅导教师 张静 成绩 实验日期2015.5.19实验时间14:00~1 ...

  2. 词法分析程序的设计(编译原理实验一)

    词法分析程序的设计(编译原理实验一) 一.实验内容 ​ 编制一个能够分析三种整数.标识符.主要运算符和主要关键字的词法分析程序. 二.实验要求 编写程序,识别如下单词符号 标识符 <字母> ...

  3. html解析器编译原理,编译原理实验报告词法分析器(内含源代码).docx

    编译原理实验报告词法分析器(内含源代码) 编译原理实验(一) --词法分析器 实验描述 运行环境:vc++2008 对某特定语言A ,构造其词法规则. 该语言的单词符号包括: 1该程序能识别的单词符号 ...

  4. 编译原理实验:代码生成作业(1)

    编译原理实验4:中间代码生成实验包-C++文档类资源-CSDN下载编译原理实验4:中间代码生成实验包更多下载资源.学习资料请访问CSDN下载频道.https://download.csdn.net/d ...

  5. 编译实验 lr c语言代码,编译原理-实验5-LR(1)分析法

    <编译原理-实验5-LR(1)分析法>由会员分享,可在线阅读,更多相关<编译原理-实验5-LR(1)分析法(6页珍藏版)>请在人人文库网上搜索. 1.编译原理实验报告项目名称 ...

  6. 编译原理--实验2 语法分析

    文章目录 前言 1.1实验目的 1.2 实验任务 1.3 实验内容 1.3.1 实验要求 1.3.2 输入格式 1.3.3 输出格式 1.3.4 样例 1.4 程序 1.4.1 程序流程图 1.4.2 ...

  7. 编译原理实验二:赋值语句的语法分析程序设计

    编译原理实验二:赋值语句的语法分析程序设计 1.1实验内容 目的: 在前面实验的基础上,通过设计.编制.调试一个典型的赋值语句的语法分析程序,实现对词法分析程序所提供的单词序列进行语法检查,进一步掌握 ...

  8. 编译原理实验:自上而下语法分析

    编译原理实验:自上而下语法分析 1. 实验题目:自上而下语法分析 实验目的 实验内容 实验要求 输入输出 2. 设计思想 3. 算法流程 4. 源程序 5. 调试数据 1. 实验题目:自上而下语法分析 ...

  9. 编译原理实验:自下而上语法分析

    编译原理实验:自下而上语法分析 1. 实验题目:自下而上语法分析 实验目的 实验内容 实验要求 输入输出 2. 设计思想 3. 算法流程 4. 源程序 5. 调试数据 1. 实验题目:自下而上语法分析 ...

  10. 编译原理实验二(全部存储到数组再逐行验证语法版.....这种思路被老师否了,应该是验证一行扔掉一行才对)

    编译原理实验二(可能还有BUG,不确定继续找) 要大改一次23333,老师的意思是不能用数组存储,而是一边识别单词,然后识别完一行就判断一次语法 写实验二的时候找到的实验一的一个逻辑错误 改动了实验一 ...

最新文章

  1. 腾讯张正友:攻克可进化机器人,6个研究趋势与7大技术突破点
  2. SQLAlchemy之SQL Expression
  3. Winform中使用DevExpress时给控件添加子控件的方法
  4. 女儿学会走路了,是不是该教她学Python了?
  5. 1024对话内核大神谢宝友
  6. lua判断字符不为空或空格_Lua判断字符串前缀是否为指定字符的3种方法
  7. mqtt如何判断设备离线_污水处理设备公司给出的价格如何判断真实性?
  8. 对字符串数组中的M个字符串按长度由小到大进行排序
  9. blog.1z5k.com
  10. spss案例教程主成分分析与因子分析及SPSS实现
  11. 超详细的Redis实战笔记
  12. Dreamweaver 网页设计作业静态模板
  13. 电脑在使用b站的时候插入耳机,耳机没有声音,只能外放,其他软件可以正常使用。
  14. 一个40岁程序员的经历
  15. WKWebView 设置 UserAgent
  16. Linux 系统编程笔记-(1)基本概念
  17. docker 垃圾清理命令
  18. 「UG/NX」BlockUI 控件集合
  19. 易语言和c语言语法哪个接近点,易语言如果真、如果和判断知识点总结
  20. 红米note5解锁教程_红米Note5解锁bl教程_红米Note5获取解锁码进行一键解锁的方法...

热门文章

  1. Android Studio同步失败设置代理,Android Studio如何设置代理?
  2. linux签名服务器,linux – 如何在远程服务器上使用gpg签名密钥?
  3. html float菜鸟,这些年,我们前端菜鸟遇到的坑(1)--CSS易错点--float、透明度、rem......
  4. vo生成MySQL表_跟我学微服务统一开发平台-代码生成器
  5. android-ultra-pull-to-refresh list,[Android]Ultra-Pull-To-Refresh之listview下拉刷新、上拉加载的用例...
  6. 六十二、数据结构栈和队列的相互实现
  7. 十九、前端必学Bootstrap美化(下篇)
  8. windows平台下TensorFlow的各种安装不成功
  9. baseline发布!OPPO安全AI挑战赛,人脸识别对抗攻击赛题详解
  10. ACL 2021 | 结构化知识蒸馏方法