编译器构造 – 编写编译器,词法分析?

我是编写编译器的新手.所以我目前正在开始这个项目(用
Java编码),在编码之前,我想更多地了解词法分析部分.我在网上研究过,我发现大多数都使用了标记器.

该项目要求我不使用它们(标记器),而是使用有限状态自动机.我很困惑,我是否需要使用链接列表来实现它?或者一个简单的嵌套开关案例就可以了.我对实现有限自动机并不熟悉,有哪些优点?

最佳答案 Russ Cox的
Regular Expression Matching Can Be Simple And Fast是使用有限状态机构建识别器的一个很好的介绍.他展示了如何从正则表达式到非确定性有限自动机到确定性有限自动机.他的参考实现使用
directed graph(类似于链表,但每个节点可以有多个“out”引用,并且可以引用包括其自身在内的任何其他节点)与链表.还有其他方法来建模状态机,包括:

> Big switch statements and transition tables
> A virtual machine

您可以通过组合多个识别器来构建词法分析器/扫描仪.例如,假设一个仅赋值语言,其中包含由正则表达式定义的以下标记:

>标识符:[a-zA-Z]
>赋值:=
>号码:[0-9]
>关键字:和

当您从左向右扫描输入时,根据当前符号在每个令牌的机器中移动过渡.如果符号没有有效转换,请选择处于接受状态的最后一台机器.扫描到该状态的所有符号都是令牌的一部分.在最后接受的符号后的符号处再次开始扫描.如果新令牌没有有效转换,则输入无效,词法分析器应报告错误.如果有多台计算机处于接受状态,则优先规则应决定使用哪个令牌.

注意:这些步骤描述了始终返回最长匹配的词法分析器.您还可以设计一个lexer,只要其中一台机器处于接受状态,它就会返回一个令牌.

样本输入结果:

> a = 10 :(标识符a)(赋值=)(数字10)
> a = 10:无效 – 我们的令牌定义中不接受空格
> 25 = xyz :(编号25)(赋值)(标识符xyz)
> 25and42 :(数字25)(关键字和)(数字42) – 假设关键字优先于标识符
> b = 1 2:无效 – 我们的令牌定义中不接受”’
> andx = 8 :(标识符和x)(赋值)(数字8) – 最长匹配给我们(标识符和x)与(关键字和)(标识符x)

请注意,词法分析只返回令牌.它不知道令牌是否正确使用. ’25 = xyz’可能没有任何意义,但我们必须等到解析阶段才能确定.

作为额外的资源,Dick Grune将Parsing Techniques – A Practical Guide的第一版作为Postscript和Pdf提供.

点赞