编译器设计实战:基于Racket的增量式设计
[美] 杰里米·G.希克
译者序
编译原理在计算机科学中占据着至关重要的地位。因为高级语言的广泛使用,才有了今日无所不在的软件和绚烂多彩的信息世界,而这一过程中居功至伟的便是编译器——负责将高级语言程序转换成计算机能够执行的目标代码。编译的基本理论和方法研究主要集中在20世纪六七十年代,至20世纪70年代末80年代初基本成熟,所以就有了1986年Aho等人的经典著作(俗称“龙书”):《编译原理》。神奇的是,20年后该书才推出经修订扩充的第2版,这对于日新月异、高速发展的计算机领域而言非常罕见。其修订版的序言中有力地阐明了编译技术仍然重要的原因:“我们认识到,很少有读者会为一种主要的编程语言构建甚至维护编译器;然而,与编译器相关的模型、理论和算法可以广泛应用于软件设计和软件开发的各类问题中。”
编译原理与技术是计算机专业相对困难的一门课程,这体现在理论和实践两个方面。在理论方面,编译程序设计需要掌握上下文无关文法的分析方法——自顶向下的预测或自底向上的归约,以及相应的数据结构和算法实现,还有其他的一些理论和算法。在实践方面,困难更为明显:对任何一种稍复杂的语言,我们很难通过软件扩充的方式去实现编译器,换句话说,在一个已有的语言编译器中加入新的语言特性是非常困难的。我们可能知道在工程领域存在大量Linux或其他操作系统相关的定制工作,尤其在嵌入式的系统中;但我们在应用中很少听说过对GNU编译工具的修改或扩展。个中原因,除去需求相对少之外,复杂性大概是主要的障碍:编译器不同过程间的联系和依赖更紧密、更一体化,相关工作很多时候让人无从下手。例如,gcc编译器在转换过程中会生成寄存器传递语言(RTL)的中间代码,而该语言本身就是非常复杂的。这就意味着,为了转换新加入的语法项,需要对编译器已经实现的各种细节加以了解,这自然是非常困难的。所以,在编译课程的程序实践中,我们给出的都是一些很小的语言玩具问题,可借助…