C ++可能是static metaprogramming和Java doesn't support it最受欢迎的语言。
除C ++之外是否还有其他支持生成编程的语言(创建程序的程序)?
答案 0 :(得分:32)
模板样式元编程的替代方法是在各种Lisp实现中看到的宏样式。我建议下载Paul Graham's On Lisp,如果你对使用在JVM上运行的宏的Lisp感兴趣,也可以查看Clojure。
Lisp中的宏比C / C ++风格强大得多,并且本身构成了一种语言 - 它们用于元编程。
答案 1 :(得分:24)
让我列出少数重要细节,了解元编程如何在lisp 中运作(或scheme或{{3} },或选择你最喜欢的“动态”语言:
使用lisp元编程实现可以作为用户库的随机示例(这些是常见lisp库的实际示例):
答案 2 :(得分:13)
模板元编程实质上是滥用模板机制。我的意思是你基本上得到了你所期望的功能,这是一个无计划的副作用 - 它是一团糟,并且(尽管工具越来越好)是一个真正的痛苦,因为语言没有支持你这样做(我应该注意到,我对这方面的最新技术经验已经过时了,因为我基本上放弃了这种方法。虽然我没有听说过任何重大进展) / p>
在98年左右解决这个问题是驱使我寻找更好解决方案的原因。我可以编写依赖它的有用系统,但它们是地狱般的。四处寻找最终使我成为Common Lisp。当然,模板机制是Turing完成,但是同样是intercal。
Common Lisp做元编程“正确”。你可以使用该语言的全部功能,没有特殊的语法,并且因为语言非常动态,你可以用它做更多的事情。
当然还有其他选择。没有其他语言我使用的元编程比Lisp更好,这就是我将它用于研究代码的原因。你可能想要尝试别的东西有很多原因,但这些都是权衡取舍。您可以查看Haskell / ML / OCaml等。许多函数式语言都具有接近Lisp宏的强大功能。你可以找到一些.NET目标的东西,但它们都非常边缘(在用户群等方面)。在工业上使用的语言中,没有一个大玩家真的有这样的东西。
答案 3 :(得分:11)
Nemerle和Boo是我个人最喜欢的事情。尽管文档很差,但Nemerle的宏语法非常优雅。 Boo的文档非常好,但它的宏不太优雅。然而,两者都工作得非常好。
两者都是.NET,因此如果您使用IKVM,它们可以轻松地与C#和其他.NET语言(甚至Java二进制文件)进行互操作。
编辑:澄清一下,我的意思是Lisp意义上的宏,而不是C的预处理器宏。这些允许在编译时定义新语法和繁重的元编程。例如,Nemerle提供的宏将在编译时针对您的SQL服务器验证您的SQL查询。
答案 4 :(得分:9)
Nim是一种相对较新的编程语言,它对静态元编程提供了广泛的支持,并生成了高效的(类似C ++)编译代码。
它支持编译时功能评估,通过宏进行类似lisp的AST代码转换,编译时反射,可以使用任意值进行参数化的泛型类型,以及可用于创建用户定义的高级的术语重写类型感知的窥视孔优化。甚至可以在编译过程中执行可能影响代码生成的外部程序。例如,考虑与本地运行的数据库服务器通信,以验证代码中的ORM定义(通过某些DSL提供)是否与数据库的模式匹配。
答案 5 :(得分:6)
"D" programming language与C ++类似,但有更好的元编程支持。以下是仅使用编译时元编程编写的光线跟踪器示例:
此外,还有一个名为“Concept GCC”的gcc分支,它支持C ++没有的元编程结构(至少还没有)。
答案 6 :(得分:5)
Common Lisp支持以多种不同方式编写程序的程序。
1)程序数据和程序“抽象语法树”是统一的(S表达式!)
2)defmacro
3)阅读器宏。
4)MOP
其中,真正令人兴奋的是MOP。阅读“元对象协议的艺术”。我保证,这会改变你的想法!
答案 7 :(得分:4)
答案 8 :(得分:3)
Haskell的大量工作:领域特定语言(DSL),可执行规范,程序转换,部分应用程序,分阶段计算。很少有链接可以帮助您入门:
答案 9 :(得分:2)
'元编程'对于这个特定的功能来说真的是一个坏名字,至少当你讨论多种语言时,因为只有一小段语言需要这个功能:
取出其中任何一个,并且'静态元编程',只是没有意义。因此,如果任何远程主流语言具有类似的东西,我会感到惊讶,正如C ++所理解的那样。
当然,动态语言和几种函数式语言支持完全不同的概念,也称为元编程。
答案 10 :(得分:2)
ML系列语言专门为此目的而设计。 OCaml最着名的成功案例之一是用于高性能FFT的FFTW库,它是几乎完全由OCaml程序生成的C代码。
干杯, Jon Harrop。
答案 11 :(得分:2)
大多数人都试图找到一种具有“终极反思”的语言 用于自我检查和“eval”之类的东西,用于实现新代码。 这些语言很难找到(LISP是一个主要的反例) 他们当然不是主流。
但另一种方法是使用一组可以检查的工具, 生成和操作程序代码。累积奖金是一种工具 专注于Java。 http://jackpot.netbeans.org/
我们的DMS软件再造工具包是 这样一个工具,适用于C,C ++,C#,Java,COBOL,PHP, Javascript,Ada,Verilog,VHDL和其他各种语言。 (它使用生产质量前端使其能够读取 所有这些语言)。 更好的是,它可以在同一时刻使用多种语言。 见http://www.semdesigns.com/Products/DMS/DMSToolkit.html
DMS之所以成功,是因为它提供了一个常规方法和支持基础设施,可以完全访问作为AST的程序结构,并且在大多数情况下还有额外的数据,如符号表,类型信息,控制和数据流分析,这些都是完成复杂程序所必需的操纵。
答案 12 :(得分:1)
Lisp支持一种“元编程”形式,虽然与C ++模板元编程不同。此外,你的术语“静态”在这种情况下可能意味着不同的东西,但Lisp也支持静态类型,如果这就是你的意思。
答案 13 :(得分:1)
答案 14 :(得分:1)
使用哪种语言都没有关系-它们中的任何一个都可以执行异构生成元编程。 采用任何动态语言(例如Python,Clojure或Haskell)(如果您是打字迷),并使用该宿主语言编写可以自己编译的模型成为您想要或被团队/雇主强迫使用的主流语言。
我发现对象图是用于内部模型表示的良好模型。此图可以在单个节点中混合属性和有序子图,这是属性语法和AST固有的。因此,对象图解释可以是您的宿主语言和目标语言之间的有效层,并且可以充当在数据结构上定义的某种非语法语言。
最接近的模型是AST:以Python(宿主语言)为目标,以C ++语法(目标语言)描述AST树:
# from metaL import *
class Object:
def __init__(self, V):
self.val = V
self.slot = {}
self.nest = []
class Module(Object):
def cc(self):
c = '// \ %s\n' % self.head(test=True)
for i in self.nest:
c += i.cc()
c += '// / %s\n' % self.head(test=True)
return c
hello = Module('hello')
# <module:hello> #a04475a2
class Include(Object):
def cc(self):
return '#include <%s.h>\n' % self.val
stdlib = Include('stdlib')
hello // stdlib
# <module:hello> #b6efb657
# 0: <include:stdlib> #f1af3e21
class Fn(Object):
def cc(self):
return '\nvoid %s() {\n}\n\n' % self.val
main = Fn('main')
hello // main
print(hello.cc())
// \ <module:hello>
#include <stdlib.h>
void main() {
}
// / <module:hello>
但是,您不受构造的对象图的抽象级别的限制:您不仅可以自由添加自己的类型,而且对象图可以解释自身,因此可以像Lisp中的列表一样修改自身。