我正在阅读关于Java平台上ployglot编程的 TheServerSide上的一篇文章.文章中的一些评论将元编程称为生成代码的能力(可能即时).
元编程能否动态生成代码,或者是在运行时将方法和属性注入现有对象的能力(就像Python,Ruby和Groovy等动态语言允许的那样).
Dav*_*cia 79
元编程是指程序了解自身或可以操纵自身的各种方式.
在像C#这样的语言中,反射是元编程的一种形式,因为程序可以检查有关自身的信息.例如,返回对象的所有属性的列表.
在ActionScript等语言中,您可以在运行时评估函数以创建新程序,例如eval("x"+ i).当S为1时,DoSomething()会影响名为x1的对象,当i为2时,会影响x2.
最后,元编程的另一种常见形式是程序可以以非平凡的方式改变自己.LISP因此而闻名,这是Paul Graham十年前所倡导的.我将不得不查阅他的一些具体论文.但是这个想法是该程序将根据其状态改变程序的另一部分.这允许在运行时做出决策的灵活性,这在当今大多数流行语言中是非常困难的.
值得注意的是,回到直接组装编程的好时代,在运行时改变自身的程序是必要且非常普遍的.
保罗格雷厄姆的文章"使得Lisp与众不同":
许多语言都有一种称为宏的东西.但是Lisp宏是独一无二的.不管你信不信,他们所做的与括号有关.Lisp的设计者并没有将语言中的所有括号都放在不同的位置.对于Blub程序员来说,Lisp代码看起来很奇怪.但那些括号是有原因的.它们是Lisp与其他语言之间根本区别的外在证据.
Lisp代码由Lisp数据对象构成.并不是简单的意义上说源文件包含字符,而字符串是该语言支持的数据类型之一.Lisp代码在解析器读取之后,由可以遍历的数据结构组成.
如果你理解编译器是如何工作的,那么真正发生的事情并不是说Lisp有一个奇怪的语法,因为Lisp没有语法.您可以在解析树中编写程序,这些解析树在解析其他语言时会在编译器中生成.但是这些解析树可以完全访问您的程序.您可以编写操作它们的程序.在Lisp中,这些程序称为宏.它们是编写程序的程序.
编写程序的程序?你什么时候想做那个?不经常,如果你想在Cobol.如果你在Lisp中思考的话,一直都是.如果我能给出一个强大的宏的例子,那么在这里会很方便!那个怎么样?但如果我这样做,那对于不了解Lisp的人来说就像是胡言乱语; 这里没有空间来解释你需要知道的一切,以了解它的含义.在Ansi Common Lisp中,我试图尽可能快地移动事物,即便如此,直到第160页我才开始使用宏.
但我想我可以提出一种可能令人信服的论点.Viaweb编辑器的源代码大概是20-25%的宏.宏比普通的Lisp函数更难编写,并且当它们不必要时使用它们被认为是不好的风格.所以代码中的每个宏都存在,因为它必须存在.这意味着该程序中至少有20-25%的代码正在执行您不能轻易用其他任何语言执行的操作.然而,对于Blub程序员可能对我对Lisp的神秘力量的主张持怀疑态度,这应该让他感到好奇.我们不是为了自己的娱乐而编写这段代码.我们是一个小小的创业公司,我们尽可能努力编程,以便在我们和竞争对手之间设置技术障碍.
一个可疑的人可能会开始怀疑这里是否存在某种相关性.我们的代码中有很大一部分是在做其他语言很难做的事情.由此产生的软件做了竞争对手软件无法做到的事情.也许有某种联系.我鼓励你遵循这个主题.可能还有更多的老人在他的拐杖上蹒跚而行,而不是眼睛.
Jon*_*rop 40
好问题.我很遗憾地看到目前没有一个答案能够正确回答你的问题.也许我可以帮忙......
元编程的定义非常简单:它意味着操作程序的程序.
你接受的答案是说操纵自己的程序.这些确实是元程序,但它们是所有元程序的子集.
所有:
是元程序.因此GCC编译器是元程序,CPython解释器是元程序,Mathematica计算机代数系统是元程序,Coq定理证明器是元程序等等.
其他答案断言元程序是生成其他程序的程序.这些确实是元程序,但同样,它们是所有元程序的子集.在西方最快傅立叶变换(FFTW)库是这样的元程序的一个例子.源代码主要在OCaml中编写,它生成一些C代码(称为codelet),这些代码被组合在一起以创建针对特定机器优化的高性能快速傅立叶变换例程.该库实际上用于在Matlab中提供FFT例程.自FORTRAN早期以来,几十年来人们一直在编写程序来生成数值方法.
第一种集成了元编程支持的编程语言是20世纪50年代后期的LISt处理器(LISP)语言.LISP 1.5包含许多使元编程更容易的功能.首先,LISP的核心数据类型是嵌套列表,即树状(a (b c) d)
,这意味着任何LISP代码都可以本地表示为数据结构.这被称为同质性.其次,可以使用QUOTE轻松地将LISP代码转换为数据.例如,(+ 1 2 3)
添加1 + 2 + 3并(QUOTE (+ 1 2 3))
创建一个在计算时添加1 + 2 + 3的表达式.第三,LISP提供了一个元循环求值器,允许您使用主机解释器或编译器在运行时评估LISP代码,包括运行时生成的LISP代码.LISP的后代包括Scheme和Clojure.在所有这些语言中,元编程最常见于修改自身的程序形式,通常使用宏.
在20世纪70年代,Robin Milner开发了一个MetaLanguage(ML),演变成ML系列编程语言,包括标准ML和OCaml,并强烈影响Haskell和F#.这些语言可以轻松表达其他语言.在这些语言中,元程序最常见的是词法分析器,解析器,解释器和编译器.
1994年,Erwin Unruh发现C++模板系统是Turing完整的,可以在编译时用于执行任意程序.C++模板元编程为未经洗涤的群体带来了元编程,他们(ab)将它用于许多不同的事情,包括在Blitz ++库中生成数值方法.