带编译与不带编译的exec语句
这个周末,我一直在研究Michele Simionato的decorator模块,这个模块可以创建保留函数签名的装饰器。它的核心是一个动态生成的函数,工作原理大概是这样的……
src = """def function(a,b,c) :\n return _caller_(a,b,c)\n"""
evaldict = {'_caller_' : _caller_}
code = compile(src, '<string>', 'single')
exec code in evaldict
new_func = evaldict[function]
在玩这个代码的过程中,我发现可以完全省略编译这一步,直接用一个:
exec src in evaldict
现在,我相信这个额外的步骤是有原因的,但我还没找到这两种方法之间的区别是什么。是性能问题吗?
既然我在问,能不能用eval来实现类似的功能,也就是定义一个新函数并获取它的引用?我试过,但没能成功……
2 个回答
2
compile() 这个函数可以让你控制生成的代码对象,以及它的名字和来源,而 exec 就没有这么灵活。这样做还有个好处,就是当别人阅读你的代码时,他们能明白这些是不同的步骤,并且在以后需要多次执行同样的代码时(用 compile() 编译一次,再用 exec 多次执行会更快),这样写代码也是为了让下一个阅读你代码的人更容易理解,这对设计选择来说总是有积极的影响。