有没有办法通过编程生成Python字节码?

有没有办法通过编程生成Python字节码?,python,expression-trees,abstract-syntax-tree,dsl,bytecode,Python,Expression Trees,Abstract Syntax Tree,Dsl,Bytecode,我想尝试一下Python解释器,并尝试创建一个小型DSL。是否有任何模块可以执行类似于此理论代码(类似于LINQ表达式树)的操作 或者仅仅生成Python源代码会更容易吗?使用C、SWIG或Cython是否可以简化此操作?查看此处的反汇编程序模块: 在Python2.X中,您通常会使用及其ast子模块来实现这一点(但请注意,自版本2.6以来,此模块已被弃用)。在Python3.X中,您将使用just 两者都提供了一个compile()函数,该函数将从source/AST转换为“可由exec语句或

我想尝试一下Python解释器,并尝试创建一个小型DSL。是否有任何模块可以执行类似于此理论代码(类似于LINQ表达式树)的操作


或者仅仅生成Python源代码会更容易吗?使用C、SWIG或Cython是否可以简化此操作?

查看此处的反汇编程序模块:


在Python2.X中,您通常会使用及其
ast
子模块来实现这一点(但请注意,自版本2.6以来,此模块已被弃用)。在Python3.X中,您将使用just

两者都提供了一个
compile()
函数,该函数将从source/AST转换为“可由
exec
语句或
eval()
执行的代码对象”,解释如何使用
\coding
指令指定自己的Python扩展。示例(实际格式定义在和中):


生成Python代码并运行它更容易。如果这样做,还可以更轻松地调试它,因为有实际的源代码可供调试器显示。另请参阅Malte Borchs在Python杂志7月号上的文章,他在文章中谈到了这一点。另一个答案是,通过
ast
工作并将树编译成字节码可能是最简单的;生成源代码并编译它们,几乎一样好


但是,要探索较低级别的方法,请查看以下链接:;我发现它特别有用(目前在2.6和3上都不起作用。*,只有2.4或2.5,但我认为在2.6上修复它应该很容易,正如目前在其跟踪器中讨论的那样)。我没有使用Phil Eby的类似功能,但考虑到作者的声誉,我相信值得一看

Python3的更新-还有一个非常有趣的汇编程序

事实上,在Py3中,唯一一个为我工作的人。它有非常好和干净的API:

>>> import byteasm, dis
>>> b = byteasm.FunctionBuilder()
>>> b.add_positional_arg('x')
>>> b.emit_load_const('Hello!')
>>> b.emit_load_fast('x')
>>> b.emit_build_tuple(2)
>>> b.emit_return_value()
>>> f = b.make('f')
>>> f
<function f at 0xb7012a4c>
>>> dis.dis(f)
  1           0 LOAD_CONST               0 ('Hello!')
              3 LOAD_FAST                0 (x)
              6 BUILD_TUPLE              2
              9 RETURN_VALUE
>>> f(108)
('Hello!', 108)
>导入byteasm,dis
>>>b=byteam.FunctionBuilder()
>>>b.添加位置参数('x')
>>>b.emit\u load\u const('Hello!')
>>>b.快速释放负载('x')
>>>b.emit\u build\u元组(2)
>>>b.发射返回值()
>>>f=b.make('f')
>>>f
>>>dis.dis(f)
1 0加载常数0('Hello!')
3加载速度为0(x)
6构建元组2
9返回值
>>>f(108)
(‘你好!’,108)

唯一的问题是我想汇编字节码,而不是反汇编。:-)啊,说得好,很抱歉;)然而,反汇编模块的好处在于,它可以让您查看生成的字节码以及字节码指令的细节。鉴于OO语言(尤其是Python)的巨大表达能力,DSL是相当愚蠢的。只需编写Python。如果你为自己提供好的类定义,你就有一个“类似DSL”的Python,而不需要它。我们在DSL方面的效率更高。参见“代码完成”软件构造的圣经。
# coding: pyspec

class Bow:
    def shot(self):
        print "got shot"

    def score(self):
        return 5

describe Bowling:
    it "should score 0 for gutter game":
        bowling = Bow()
        bowling.shot()
        assert that bowling.score.should_be(5)
>>> import byteasm, dis
>>> b = byteasm.FunctionBuilder()
>>> b.add_positional_arg('x')
>>> b.emit_load_const('Hello!')
>>> b.emit_load_fast('x')
>>> b.emit_build_tuple(2)
>>> b.emit_return_value()
>>> f = b.make('f')
>>> f
<function f at 0xb7012a4c>
>>> dis.dis(f)
  1           0 LOAD_CONST               0 ('Hello!')
              3 LOAD_FAST                0 (x)
              6 BUILD_TUPLE              2
              9 RETURN_VALUE
>>> f(108)
('Hello!', 108)