第一部分 介绍ANTLR和计算机语言翻译
第一章 开始antlr
本书是antlr的参考指南:一个复杂的解析程序生成器,你可以用这个解析程序实现语言的解释器,编译器或其他翻译器。这不是一本编译器的书,也不是语言理论的教科书。虽然你能找到很多关于编译器和编译原理基础的书,但很多语言类应用并不是编译器。这本书更适合构建普通,日常使用的语言类应用。本书附带大量例子,解释和参考资料,立足于一个语言工具和方法。
程序员常使用antlr来构建领域语言(简称DSLs)的翻译器和解析器.DSls通常是面向特定任务的高级语言。他们设计的目的尤其是为了在某个领域用户使用的效率。DSLs有很大的应用范围,很大一部分你可能不认为他们是语言。DSLs包括数据格式,配置文件格式,网络协议,文本处理类语言,蛋白模型,基于序列,太空控制器语言和某些特定领域内的编程语言。
DSLs尤其对软件开发很重要,因为你只是简单的使用这个语言编写软件,就可以以一种很自然的,高保真的,健壮的和可维护的方式将一个问题封装起来。例如,美国航天局就为太空任务使用一种航天特定的命令语言,来提高可重用性,降低风险和成本,提高开发速度。甚至上世纪六十年代首次阿波罗项目中的导引控制器就使用DSLs来进行向量计算(http://www.ibiblio.org/apollo/assembly_language_manual.html)。
本章介绍antlr的主要部件以及他们如何组织在一起。你会看到一个DSL 翻译问题如何被分解为多个更小的问题。这些更小问题就是一些固有的翻译阶段(词法,解析,树解析这些阶段),这些阶段使用固有的数据类型和结构(文本字符,标记符,树,如符号表等的辅助结构)来通讯的。阅读完本章节之后,你会大大的熟悉antlr的这些部件,可以应对本章之后的细节讨论。让我们从蓝图开始吧。
1.1 蓝图
一个翻译器将一种语言的每个句子映射为输出句子。为了映射,翻译器会对输入符号,执行你提供的代码。翻译器必须对不同的句子执行不同的动作,这意味着必须能够识别出不同的句子。
如果将识别器分解为两个类似但不同的任务或阶段,识别器就变得容易多了。这两个阶段模拟我们如何读英文。你不会一个字母一个字母的读句子,而是认为句子有一串单词组成。人脑潜意识的将字母组合成单词,在字典中找到单词,然后进行语法结构识别。第一个阶段叫词法分析,作用在输入的字母上。第二个阶段为解析,作用在词汇上,叫标记(从第一个阶段产生的)。antlr通过你提供的语法自动生成词法分析器和解析器。
执行翻译通常就是在语法中嵌入动作(代码)。antlr按照在语法中的 位置来执行这些动作。按照这种方式,你可以对不同的短语(一个句子中的片段)执行不同的代码。比如表达式规则中的动作,只有在解析器将句子识别为表达式时候才执行。
一些翻译要分解为更多的阶段。经常翻译过程需要进行多遍,在一些情况下,在多个阶段里,大大的容易编码。相比每个阶段去解析输入的文本,构造一种在不同阶段之间传递的中间形式,这样会更好。
图1.1:翻译器数据流程:边代表数据结构,正方形代表各个阶段。(译者:图中有characters, tokens, AST 3种数据结构,lexer, parser, tree walker 3个阶段)
这个中间形式通常是课树结构,叫抽象语法树(AST),是高度处理的、对输入的压缩版本。每个阶段都搜集更多信息或执行更多的计算。在最后阶段,生成器阶段,使用前面所有阶段的数据结构和计算结果,生成输出。
图1.1示例了一个翻译器接受字符输入,生成输出的基本数据流程。词法分析器或者叫词法器,将输入的字符分解为标记。解析器接受这些标记,并且试图识别句子结构。最简单的翻译器执行输出结果这个动作,忽略其他后续阶段(过程)。
另一种简单的翻译器仅仅构造某种内部数据结构———不输出任何内容。读取配置文件就是这种翻译器的最后例子。更复杂的翻译器仅使用解析器去构造AST。多个树遍历器(深度优先)再遍历AST,为后续阶段计算出对应的其他数据结构和信息。虽然在这个图中看不出来,最后的生成器能根据模版产生结构化的文本内容。
模版就是一个带有参数的文本文档,生成器可以给这些参数赋值。这些参数也可以是对传入的数据进行计算的表达式。Antlr集成了StringTemplate引擎,这样可以更容易的构造生成器(参见第九章 使用模版和语法生成结构化文本)。
StringTemplate是从内部数据结构生成结构化文本的面向领域的语言,有点输出语法的意思。特征包括模版组继承,模版多态,迟计算,递归,输出自动缩进。Stringtemplate是在解决复杂系统中遇到的实际问题中成熟起来的。Antlr很大程度上使用stringtemplate来将语法翻译为可执行的识别器代码。每个antlr目标语言(如java代码,c代码)都是一组纯粹的模版,被antlr内部的重定向代码生成器使用。
好,让我们仔细看看在上页中图1.1中在各个阶段传递的数据对象。在下页的图1.2中,说明了字符,标记,AST之间的关系。词法器接受ANTLRStringStream或ANTLRFileStream等CharStream提供的字符。这些预先定义的Stream会将整个输入装进内存,然后将这些字符缓存起来。没有为标记建立单独的字符串对象,但标记可以被追踪在字符缓存中的索引位置。
类似的,没有将数据从标记中复制到树节点中,ANTLR AST节点简单指向创建他们的标记。例如,CommonTree,是预先定义的含有标记指针的节点。ANTLR AST 节点的类型被认为是 Object(对象),这样在你树节点上的数据类型就没有限制。(…)下页中图1.2描述的数据类型之间的关系是很高效和灵活的。
在图中有检查框的标记位于解析器看不到的隐藏通道。解析器可以调到一个通道上,这样忽略其他通道上的任何标记。在词法器上搞点小动作,你可以将不同的标记在不同通道上发给解析器。例如,在解析java时候,你可能会想将空格和普通注释在一个通道上,javadoc注释放在另一个通道上。标记缓存区保留相关标记而不考虑他们的通道号。标记通道号机制对忽略但不扔掉空格和注释(因为一些翻译器需要保留格式和注释)这个问题是个极好的解决办法。
图1.2 字符串,标记,抽象语法树之间的关系;CharStream,Token,CommannTree是antlr运行时期数据类型
牢记下节的模拟或许对你看本书后面的例子和讨论有帮助。
1.2 一个迷宫的比喻
本书主要聚焦2个主题:发现在输入语句后的隐藏树结构和生成结构化文本。第一眼,你可能对本书中的一些语言术语和技术感到陌生。别急,我会定义和解释所有,但你读的时候记住下面的比喻是有用的。
想象下一个迷宫,只有一个入口和出口,在地板上写着单词。每条按顺序读出从入口到出口的单词生成一个句子。感觉上,迷宫就好像是定义一种语言的语法。
你也可以把迷宫想象成句子识别器。给定一个句子,你可以按顺序将句子中的单词和地板上的单词匹配起来。任何能将你引导到出口的句子都是正确的句子(或短语),按照这个迷宫定义的语言。
语言识别器必须发现句子隐含的部分树结构,每次一个单词。几乎对每个单词,识别器必须做出一个短语(或子短语)的解释决定。有时这些决定会很复杂。比如,有时一个决定需要参考前面的决策或甚至后面的决策。但大部分时间,只需要前瞻一点即可。前瞻信息类似于第一个单词或你在迷宫岔路口沿路看到的单词。在岔路口,句子中的下个单词会告诉你要走哪条路,因为沿每条路的单词是不同的。第二章,计算机语言特性,使用这个类比,更详细的描述了计算机语言特性。你也可以先读那一章,或直接跳到第三章,antlr快速开始。
在下面2节中,你会看到怎样将图1.1中的蓝图变为java代码,如何执行antlr。
1.3 安装ANTLR
Antlr使用java编写,所以就算你打算使用antlr生成Python,也要在机器上安装java。Antlr需要的java版本为1.4或以上。你先要下载(http://www.antlr .org/download.html),并解压到适当目录。你不必运行配置脚本或修改配置文件就可以正确安装antlr。如果你安装antlr到目录 /usr/local/antlr-3.0,如下:
$ cd /usr/local
$ tar xvfz antlr-3.0.tar.gz
antlr-3.0/
antlr-3.0/build/
antlr-3.0/build.properties
antlr-3.0/build.xml
antlr-3.0/lib/
antlr-3.0/lib/antlr-3.0.jar
...
$
作为3.0,antlr v3 还使用了以前antlr 版本,也就是2.7.7,还有 StringTemplate 3.0.这就是说你为了运行antlr工具必须要有这2个包。但运行生成的解析器,你不需要 antlr 2.7.2,也不需要stringtemplate 3.0(除非你使用了构造模版规则)。Java会从CLASSPATH环境变量来寻找含有.class文件的包文件和目录。你必须修改CLASSPATH环境变量来包含antlr-2.7.2.jar, stringtemple-3.0.jar 和antlr-3.0.jar。
安装唯一可能出错的地方就是设置CLASSPATH不正确或者在CLASSPATH里有另一个版本的antlr。注意其他java库(比如BEA的WebLogic)可能在你不知道的情况下使用antlr。
在Mac OS X和其他类 unix等使用bash的shell中,如下:
$ export CLASSPATH="$CLASSPATH:/usr/local/antlr-3.0/lib/antlr-3.0.jar:\
/usr/local/antlr-3.0/lib/stringtemplate-3.0.jar:\
/usr/local/antlr-3.0/lib/antlr-2.7.7.jar"
$
别忘了export。没这个,你随后启动的子进程如java则看不到这个环境变量。
在windows xp上设置CLASSPATH,你要通过 系统属性|高级 来设置。点击 系统变量,再点击在变量列表上面的新建。同样注意windows上的路径分隔符是分号(;)而不是冒号(:)。
现在,你的antlr准备好运行了。下节给了一个简单的语法例子,你可用来检查antlr是否正确安装了。
1.4 执行 ANTLR,调用识别器
一旦安装好antlr,你就可以将语法翻译为可执行的java代码了。这是个简单语法:
文件名T.g:
grammar T;
/** Match things like "call foo;" */
r : 'call' ID ';' {System.out.println("invoke "+$ID.text);} ;
ID: 'a'..'z'+ ;
WS: (' '|'\n'|'\r')+ {$channel=HIDDEN;} ; // ignore whitespace
在org.antlr.Tool类中有主程序,在语法T.g上执行antlr:
$ java org.antlr.Tool T.g
ANTLR Parser Generator Version 3.0 1989-2007
$ ls
T.g TLexer.java T__.g
T.tokens TParser.java
$
你看到了,antlr除生成了词法器——TLexer.java, 解析器——TParser.java,还有几个支持文件。
为了测试语法,你要有个主程序,来调用语法中的开始规则r。下面这个程序Test.java,就体现了图1.1中的数据流程中一部分:
Test.java
import org.antlr.runtime.*;
public class Test {
public static void main(String[] args) throws Exception {
// create a CharStream that reads from standard input
ANTLRInputStream input = new ANTLRInputStream(System.in);
// create a lexer that feeds off of input CharStream
TLexer lexer = new TLexer(input);
// create a buffer of tokens pulled from the lexer
CommonTokenStream tokens = new CommonTokenStream(lexer);
// create a parser that feeds off the tokens buffer
TParser parser = new TParser(tokens);
// begin parsing at rule r
parser.r();
}
}
编译和运行测试:
$ javac TLexer.java TParser.java Test.java
$ java Test
call foo;
EOF
invoke foo
$
输入 “call foo;“紧跟回车, 翻译器输出”invoke foo“ 紧跟回车. 注意你要输入 文件结束符(EOF)(译者:在dos下是Ctrl+Z, unix下是Ctrl+D)来终止键盘输入,否则将一直等待你的输入. 这个例子没有含有一些辅助数据结构或中间形式的树结构, 而在语法内嵌入的动作直接输出 “invoke foo“.
开发语法之前,你应该熟悉下节要讲的antlrWorks。当你构造或调试语法时,这个antlr GUI(图形界面) 会使你生活轻松得多。
1.5 语法开发环境—ANTLRWorks
图1.3,ANTLRWorks 语法开发环境|语法编辑器视图
ANTLRWorks 是Jean Bovet开发的工作在antlr上,帮助你修改、浏览、调试语法的图形工具(see http://www.antlr.org/works)。可能最重要的是,它帮你解决语法分析中的错误,而手工找出很难。AntlrWorks有以下主要特征:
图1.4,在解析java代码时的antlrWorks调试器。输入、解析树和语法在任何时候总是同步的。
ANTLRWorks使用高可移植的java(使用Swing)编写,使用BSD许可的开源项目。因为antlrWorks 和运行的解析器使用套接字通信,所以antlrworks 调试器可工作在任何antlr 目标语言上。
前面的图1.3,显示的是 在语法的动作(action)中的 “跳转到规则“ 弹出对话框。正如你期待的,antlrworks 有 规则和标记的自动完成和语法加亮。下面的面板显示的是java语法中的规则 field的语法图。当语法中有歧义和其他不确定时,语法图显示可以识别你输入的多条路径。通过这个可视化,你能直接解决这些歧义。本书第三部分 antlr的LL(*)解析细节策略,大量使用了antlrworks提供的对不确定路径的可视化。
图1.4,示例了antlrworks的调试器。调试器提供了很多信息,而且你也看到了,总能使各种视图同步。在这个例子中,语法将输入(Input)中的lexer标识和语法元素 Identifier匹配;解析树面板显示输入所隐含的树结构。更多antlrworks信息,参考用户手册(http://www.antlr.org/works/doc/antlrworks.pdf)。
本章介绍使你对antlr是什么和如何使用有一个整体了解。下一章示例了如何从语言的特性推导出为了规范语言而使用语法。第一部分的最后一章即第三章,“快速开始“,通过构造一个计算器,演示了antlr的更多特征。
- 大小: 19.1 KB
- 大小: 29.4 KB
- 大小: 91.4 KB
- 大小: 61.2 KB
分享到:
相关推荐
antlr4权威指南,适合想要构建自己的语言的同学,使用antlr4构建更方便
antlr4权威指南中文版,原书作者terence Parr,清晰版本
在《ANTLR4权威指南》这本书中,读者将全面了解ANTLR 4的工作原理,学习如何定义和使用语法规则,以及如何利用ANTLR 4进行实际项目开发。书中涵盖了从基本概念到高级特性的详细讲解,同时提供了丰富的实例和实战指导...
ANTLR(ANother Tool for Language Recognition)是一个强大的解析器生成器,用于读取、处理、执行或翻译结构化文本或二进制文件。ANTLR被广泛应用于构建语言、工具和框架,如编程语言、配置文件格式、协议、文档...
ANTLR—Another Tool for Language Recognition,其前身是PCCTS,它为包括Java,C++,C#在内的语言提供了一个...第一章Hello World 第二章 编译原理基础知识 第三章 词法分析 第四章 语法分析 第五章 嵌入文法的Actions
这本书《The Definitive ANTLR 4 Reference》是ANTLR 4的主要作者Terence Parr的著作,被誉为学习ANTLR 4的权威指南。书中详细介绍了ANTLR 4的设计理念、工作原理以及如何使用ANTLR 4来构建解析器和词法分析器。以下...
antlr指南 第四章语法分析 出自www.antlr.org.cn
antlr第五章Action协助分析 出处www.antlr.org.cn
Java Antlr 4 是一个强大的解析工具,用于生成解析器和词法分析器,它使得开发者可以轻松地处理各种语言的语法。Antlr 4 支持多种编程语言,包括 Java,C#,Python,JavaScript 等,而在这个“java Antlr 4 语法文件...
描述中提到,这个资源是基于 ANTLR 4 权威指南第四章的计算器示例,该示例已经被成功地移植到 C++ 并在 Linux 环境下进行了测试。 ANTLR 4 的核心功能是解析词法和语法。在这个计算器项目中,`LabeledExpr.g4` 文件...
antlr4权威指南
antrl4权威指南pdf
从标题“Definitive ANTLR 4 Reference”和描述“ANTLR 4的权威参考”可以看出,这本书详细介绍了ANTLR 4的所有核心功能和特性,是学习和使用ANTLR 4的重要资源。 ANTLR 4的主要特点包括: 1. **高级语法定义**:...
"ANTLR-4-Resource-Code" 提供的是《ANTLR 4权威指南》一书中的源代码,这些源代码是书中示例的实现,对于学习ANTLR 4 的语法定义、解析树构建、错误处理等核心概念非常有帮助。通过查看和分析这些源代码,读者可以...
ANTLR—Another Tool for Language Recognition,其前身是PCCTS,它为包括Java,C++,C#在内的语言提供了一个...第一章Hello World 第二章 编译原理基础知识 第三章 词法分析 第四章 语法分析 第五章 嵌入文法的Actions
ANTLR4 是一个强大的解析器生成器,用于读取、处理、执行或翻译结构化文本或二进制文件。它广泛应用于构建语言、工具和框架,包括SQL、Java、C#、JavaScript、Python等。在本项目中,"Antlr4 C++ 计算器"是一个基于...
antlr指南第三章词法分析 出自www.antlr.org.cn
《ANTLR 4权威指南》是Terence Parr编写的一本关于ANTLR(ANother Tool for Language Recognition)的图书,它专门介绍了ANTLR版本4的相关知识。ANTLR是一个非常强大和灵活的工具,用于解析形式语言,被广泛用于构建...