一个简易的词法分析器

一个简易的词法分析器

2016年06月09日 00:55:22 lishuhuakai 阅读数 2972 文章标签: Compiler词法分析更多

分类专栏: Compiler

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。

本文链接:https://blog.csdn.net/lishuhuakai/article/details/51617803

4月12日

基本上已经完工了,文章已经发布了:http://blog.csdn.net/lishuhuakai/article/details/70140914

4月10日

这个玩意远远比我想象中的要来得简单,说实话,不用一个月,估计一个星期,我就能做到七七八八,所以,人啊,不要被自己的想象力给吓到了,一切没有那么困难,在3月23日的时候,我想,一定要花一年的时间,敲出一个简易的yacc,在4月4日的时候,我认为一个月的时间足以完成这个yacc,现在呢,4月10日,我认为再来一个星期就足够了,所以,你看,真是有意思呢.

话说,做完这个玩意的话,你接下来打算干什么?至少从做完这个小型的Project之后,一直到找工作前,我估计很难再花一整段的时间来干另外的一个小型的项目,当然,说不定啦,指不定像一个多月前的脑袋发热,想弄一个yacc和正则式引擎,然后不顾一切在一个多月里鼓捣出来了,这滋味,现在想起来也足够酸爽的.

接下来的一段时光里,如果能够脑袋发热,再好不过了,发不了的话,估计就可以开启大规模的复习,整理啦,读数据结构,一步一步开始实现自己的标准库,读算法,刷leetcode,刷template,事情总是有的,也总是做不完的.

总体而言,需要为找工作开始做准备了.

4月7日

时间真的如流水啊,今天好了一点,对于怎样实现这个简化版的yacc,我差不多已经成竹在胸了,剩下的,只能每天敲一点,每天敲一点,花费一点时间和气力来逐步完成这个东西.这个东西的代码量,我估计是在3000~4000行左右,别看不大,写起来真的挺费劲的.有非常多的细节需要处理,东西自然是越简单越好.总之是一个Demo性质的Project.

4月6日

构建LALR(1)查找表的代码已经完成,下一步打算实现读入文本里的规则,话说,c++标准库里的正则表达式真心烂,连命名捕获都没有实现,没办法,我只能一个一个正则表达式来遍历,从而实现词法分析器.

4月5日

完成了FIRST`FOLLOW集查找的算法,正在实现LALR(1)表格的构建算法.写到一半,发现是在不想写了,所以出去逛游了一圈.

2017年4月4日清明节记要

好吧,这篇文章也没有多少人看,我干脆将开发的状态,开发时想吐槽的一些东西统统写在这里.

距离上一次写完正则表达式引擎又过去了一段时间,3月23号一直到4月4号,这其中间隔了大约12天左右,这些天里,我并没有闲着,索性将上学期落下的< Parsing Technology -- A Practical Guide>读了一遍,其实也没有全部读完,大概读到了LALR(1)这部分内容,个人觉得读到这一部分真的够了,因为这些知识已经足够你来实现一个核心版的yacc了,在读书的期间,顺带将看到的大部分算法都实现了一遍,从LL(1),LR(0)LR(1),还有其余各种东西.现在的话,对于怎样来实现一个yacc,我基本上算是有底了.

废话不多说,从明天起,应该一个月的时间足够我写出一个比较完善的小型的yacc了.第一个版本,我打算只实现一些基本的功能,比如说,读取文法定义的文件,构建出文法在内存中的表示,然后根据文法构建出LALR(1)表格,这里面肯定会用到正则表达式,但是我暂时还不打算使用自己之前写的正则表达式,因为可能存在bug,所以,先用c++标准库里自带的正则表达式做了再说.

第一个版本不会用到太多的自定义的结构,但是在后续不断重构的版本中,我是肯定要加入自己定义的一些容器的,因为说实在的,stl的那些容器,真的无法满足需求,为了实现相应的功能,我不得不写一大坨的代码,十分不美观,第一个版本先将功能实现再说.接下来就会陆陆续续加强自己写的这个正则表达式引擎,然后替换掉stl的正则表达式.

好了,接下来的一个月会是极其充实的一个月.毕竟,我研究生期间,可能代码量最大,持续时间最长的项目,就是这个玩意了.

一个更加简洁的parser (2017年3月23日)

如何将正则表达式变成一棵语法树,这是一个很有意思的问题.之前的几个版本中,我使用的是堆栈式计算器的原理,虽然也能够成功实现正则表达式的转换,但是通用性并不好,而且有非常多需要特殊处理的地方,更加令人头疼的是,调试起来非常花时间,所以并不是很推荐这种写法.

所以,我实现了一个更加简单的parser,自顶向下,递归分析,这种方法在编译原理里面经常用得到,核心思想就是你事先将正则表达式的文法写好,难的只是写文法而已,程序纯粹按照文法来写,非常简单,通用性也好,而且正则表达式的文法也非常简单,当然,我写的这个只是一个demo,最核心的东西已经实现了,更多的一些细节我也懒得去管.

就这样吧,希望在今年下半年找工作之前,完成一个yacc,这样的话,研二就无悔了.

版本3 (2017年3月20日更新)

这个版本功能基本上实现了,但是还有一些非常小的bug要修,看着现在写的东西有写不爽,代码应该还可以写得漂亮一些.

说真的,写这个版本的正则表达式确实有一点难度,不过还好,通过写这个东西可以学到很多东西,可以全方位锻炼代码能力,好了,容我多修几天bug,然后再放上来吧.

现在不是很想写了,因为其余都是一些边边角角的东西,难度不大,但是很费时间,所以暂时先放下了.项目还在原来的地址,https://github.com/lishuhuakai/Regular-Expression

版本2 (2017年3月16日更新)

第一个版本虽然是实现了功能,但是代码不够漂亮,因此,我重新用cpp实现了一遍,采用的算法也不是原来的算法了,具体参考了vczh的<<构造可配置词法分析器>>与<<构造正则表达式引擎>>里面的算法,但是现在只是实现了纯正的正则式匹配,代码在这里:https://github.com/lishuhuakai/Regular-Expression

代码的可读性得到了非常大的提高,相信如果参照那两篇文章,代码应该读起来没有多少困难,因为基本上用的全部是里面的算法.

对于扩展的正则式匹配,我会继续参考vczh的两篇文章,继续来实现,好吧,其实算法我已经读懂了,实现起来并没有太大难度,但是现在暂时没有时间,但是在两周之内吧,我会把<<构造可配置词法分析器>>里面提到的各种功能实现,那个应该算是版本3了.

版本1

代码大概1000行左右,使用了C++进行编写,实现的功能主要是将正则式转换成为一棵二叉树,然后对于这棵二叉树的结构,递归地来构建NFA,然后通过Thompson的方法将这个NFA转换成为了DFA,当然,我这里直接用表格的方式来表示DFA,所以后面的Hopcroft算法将DFA最小化可能并没有太多的意义,随意我将这个算法包裹了起来。不过我也完整的实现了Hopcroft算法。

当然,正则式支持不完整,只支持*,|,()以及连接操作。不过一般而言,所有的其余的正则式只是这三种东西的语法糖而已。当然,这里可没有什么正则式的错误检查,请务必保证正则式的正确性,不然有可能发生了不可预料的错误。

IDE用的是VS2013,当然很容易移植,我只用了C++标准库里面的一些结构。推荐看网易云课堂里面的编译原理课程,书籍用的是编译器设计。

代码在这里:https://github.com/lishuhuakai/Compiler/tree/master/hw03!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值