一个简单的EBNF范式的实现
在看书的时候发现了这个东西
刹那间突然觉得大学时候编译原理书上的的什么语法分析书、上下文无关等晦涩难懂的概念清晰了许多
今天把它贴出来
希望也能让你回想起些往事。。。
至于EBNF范式是什么东西,网上有详细的介绍,在此就不作赘述。
在这里,使用EBNF范式来实现一个简单算术运算的语法描述,然后用C语言实现。
该算术运算要实现的功能:
(1)能够进行加法、乘法运算,且乘法优先于加法运算
(2)实现'('、')'运算,且其优先级高于乘法运算
使用EBNF范式修改后的简单整数算术运算的语法描述:
expr-->expr+term|term
term-->term*factor|factor
factor-->(expr)|number
number-->number digit|digit
digit-->0|1|2|3|4|5|6|7|8|9
实现代码如下:
#include<stdio.h>
#include<stdlib.h>
#include<ctype.h>
int token; //holds the current input character for the parse
void error(void)
{
printf("parse error\n");
exit(1);
}
void getToken(void)
{
token=getchar();
}
void match(char c)
{
if(token==c) getToken();
else error();
}
//command-->expr'\n'
void command(void)
{
int result=expr();
if(token=='\n')
printf("The result is :%d\n",result);
else error();
}
//expr-->term { '+' term}
int expr(void)
{
int result=term();
while(token=='+')
{
match('+');
result+=term();
}
return result;
}
//term-->factor { '*' factor}
int term(void)
{
int result=factor();
while(token=='*')
{
match('*');
result*=factor();
}
return result;
}
//factor-->‘(’ expr ')' | number
int factor(void)
{
int result;
if(token=='(')
{
match('(');
result=expr();
match(')');
}
else
result=number();
return result;
}
//number-->digit { digit }
int number(void)
{
int result=digit();
while(isdigit(token))
{
result=10*result+digit();
}
return result;
}
//digit-->'0'|'1'|'2'|'3'|'4'|'5'|'6'|'7'|'8'|'9'
int digit(void)
{
int result;
if(isdigit(token))
{
result=token-'0';
match(token);
}
else
error();
return result;
}
void parse(void)
{
getToken();
command();
}
main()
{
parse();
return 0;
}
一个简单的EBNF范式的实现的更多相关文章
- 扩展Python模块系列(二)----一个简单的例子
本节使用一个简单的例子引出Python C/C++ API的详细使用方法.针对的是CPython的解释器. 目标:创建一个Python内建模块test,提供一个功能函数distance, 计算空间中两 ...
- 正则语言引擎:一个简单LEX和YACC结合运用的实例
本文先描述了LEX与YACC的书写方法.然后利用LEX与YACC编写了一个简单正则语言的引擎(暂时不支持闭包与或运算),生成的中间语言为C语言. 正则引擎应直接生成NFA或DFA模拟器的输入文件,但在 ...
- 从一个简单的约束看规范性的SQL脚本对数据库运维的影响
之前提到了约束的一些特点,看起来也没什么大不了的问题,http://www.cnblogs.com/wy123/p/7350265.html以下以实际生产运维中遇到的一个问题来说明规范的重要性. 如下 ...
- 用25行JavaScript语句实现一个简单的编译器
原文:https://www.iteye.com/news/32680 译者注:即使对于专业程序员来说,构造一个编译器也是颇具挑战性的任务,本文将会引导你抽丝剥茧,一探究竟! 我已经写了几篇与编程语言 ...
- 哪种缓存效果高?开源一个简单的缓存组件j2cache
背景 现在的web系统已经越来越多的应用缓存技术,而且缓存技术确实是能实足的增强系统性能的.我在项目中也开始接触一些缓存的需求. 开始简单的就用jvm(java托管内存)来做缓存,这样对于单个应用服务 ...
- 在Openfire上弄一个简单的推送系统
推送系统 说是推送系统有点大,其实就是一个消息广播功能吧.作用其实也就是由服务端接收到消息然后推送到订阅的客户端. 思路 对于推送最关键的是服务端向客户端发送数据,客户端向服务端订阅自己想要的消息.这 ...
- ASP.NET Aries 入门开发教程2:配置出一个简单的列表页面
前言: 朋友们都期待我稳定地工作,但创业公司若要躺下,也非意念可控. 若人生注定了风雨飘摇,那就雨中前行了. 最机开始看聊新的工作机会,欢迎推荐,创业公司也可! 同时,趁着自由时间,抓紧把这系列教程给 ...
- 计算机程序的思维逻辑 (60) - 随机读写文件及其应用 - 实现一个简单的KV数据库
57节介绍了字节流, 58节介绍了字符流,它们都是以流的方式读写文件,流的方式有几个限制: 要么读,要么写,不能同时读和写 不能随机读写,只能从头读到尾,且不能重复读,虽然通过缓冲可以实现部分重读,但 ...
- 如何开发一个简单的HTML5 Canvas 小游戏
原文:How to make a simple HTML5 Canvas game 想要快速上手HTML5 Canvas小游戏开发?下面通过一个例子来进行手把手教学.(如果你怀疑我的资历, A Wiz ...
随机推荐
- 树状数组 Playrix Codescapes Cup (Codeforces Round #413, rated, Div. 1 + Div. 2) C. Fountains
C. Fountains time limit per test 2 seconds memory limit per test 256 megabytes input standard input ...
- HDU-4825 Xor Sum,字典树好题!
Xor Sum 一遍A了之后大呼一声好(keng)题!debug了两小时~~~~百度之星资格赛,可以. 题意:给你一个n个元素的数组,m次查询,每次输入一个数k要求从数组中找到一个数与k异或值最大,输 ...
- SQL indexOf、lastIndexOf
DECLARE @Name NVARCHAR (50)SET @Name = 'abcd.12345.efght' DECLARE @Position INT --sql first indexofS ...
- HackerRank# Stock Maximize
原题地址 不知道为什么要用动态规划做,明明是扫几遍就行了啊 HackerRank上的题目特别喜欢long long类型啊,不用就爆.. 代码: #include <cmath> #incl ...
- [luoguP2518][HAOI2010]计数(数位DP)
传送门 重新学习数位DP.. 有一个思路,枚举全排列,然后看看比当前数小的有多少个 当然肯定是不行的啦 但是我们可以用排列组合的知识求出全排列的个数 考虑数位dp 套用数位dp的方法,枚举每一位,然后 ...
- Swift3.0 函数闭包与 Block
刚接触Swift,如有不对,欢迎指正 Swift中定义一个基本函数 //定义一个函数,接收一个字符串,返回一个String类型的值 func test(name:String) -> Strin ...
- asp.net 错误 类型"xxxxx"同时存在于"xxx.dll"和"xxxx.dll" 中
http://walttoney.blog.163.com/blog/static/127685797201051112839328/错误 类型“System.Web.UI.ScriptManager ...
- CodeForces 731C Socks
http://codeforces.com/problemset/problem/731/C 并查集+贪心 将要求颜色相同的袜子序号放入一个集合中 贪心:然后统计这个集合中出现次数最多但颜色 可以得到 ...
- 洛谷 [P4151] 最大异或和路径
线性基 首先我们发现,对于一条路径走过去再走回来是没有意义的, 所以我们可以没有任何其他影响的取得一个环的异或和 所以我们预处理出来所有环的异或和,求出他们的线性基,然后任找一条 \(1 \sim n ...
- 玩转css样式选择器----当父元素有多个子元素时选中第一个