如何在Python中执行包含Python代码的字符串?

时间:2009-03-31 16:12:20

标签: python string exec

如何在Python中执行包含Python代码的字符串?

14 个答案:

答案 0 :(得分:276)

对于语句,请使用exec(string)(Python 2/3)或exec string(Python 2):

>>> mycode = 'print "hello world"'
>>> exec(mycode)
Hello world

当您需要表达式的值时,请使用eval(string)

>>> x = eval("2+2")
>>> x
4

然而,第一步应该是问问自己是否真的需要。执行代码通常应该是最后的手段:如果它可以包含用户输入的代码,那么它是缓慢,丑陋和危险的。您应该首先考虑替代方案,例如更高阶的功能,看看它们是否能更好地满足您的需求。

答案 1 :(得分:60)

在示例中,使用exec函数将字符串作为代码执行。

import sys
import StringIO

# create file-like string to capture output
codeOut = StringIO.StringIO()
codeErr = StringIO.StringIO()

code = """
def f(x):
    x = x + 1
    return x

print 'This is my output.'
"""

# capture output and errors
sys.stdout = codeOut
sys.stderr = codeErr

exec code

# restore stdout and stderr
sys.stdout = sys.__stdout__
sys.stderr = sys.__stderr__

print f(4)

s = codeErr.getvalue()

print "error:\n%s\n" % s

s = codeOut.getvalue()

print "output:\n%s" % s

codeOut.close()
codeErr.close()

答案 2 :(得分:20)

请记住,版本3 exec是一个功能!
所以请始终使用exec(mystring)代替exec mystring

答案 3 :(得分:19)

evalexec是正确的解决方案,可以更安全的方式使用它们。

正如Python's reference manual中所讨论并在this教程中明确解释的那样,evalexec函数需要两个额外的参数,允许用户指定全局和局部函数和变量可用。

例如:

public_variable = 10

private_variable = 2

def public_function():
    return "public information"

def private_function():
    return "super sensitive information"

# make a list of safe functions
safe_list = ['public_variable', 'public_function']
safe_dict = dict([ (k, locals().get(k, None)) for k in safe_list ])
# add any needed builtins back in
safe_dict['len'] = len

>>> eval("public_variable+2", {"__builtins__" : None }, safe_dict)
12

>>> eval("private_variable+2", {"__builtins__" : None }, safe_dict)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<string>", line 1, in <module>
NameError: name 'private_variable' is not defined

>>> exec("print \"'%s' has %i characters\" % (public_function(), len(public_function()))", {"__builtins__" : None}, safe_dict)
'public information' has 18 characters

>>> exec("print \"'%s' has %i characters\" % (private_function(), len(private_function()))", {"__builtins__" : None}, safe_dict)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<string>", line 1, in <module>
NameError: name 'private_function' is not defined

实质上,您正在定义将在其中执行代码的命名空间。

答案 4 :(得分:11)

eval()仅用于表达式,而eval('x+1')有效,eval('x=1')不起作用。在这种情况下,最好使用exec,甚至更好:尝试找到更好的解决方案:)

答案 5 :(得分:9)

使用exec完成代码执行,与以下IDLE会话一样:

>>> kw = {}
>>> exec( "ret = 4" ) in kw
>>> kw['ret']

4

答案 6 :(得分:8)

避免使用execeval

在Python中使用execeval非常不受欢迎。

有更好的选择

从最重要的答案(强调我的):

  

对于陈述,请使用exec

     

当您需要表达式的值时,请使用eval

     

然而,第一步应该是问问自己是否真的需要。 执行代码通常应该是最后的位置:如果它可以包含用户输入的代码,那么它是缓慢,丑陋和危险的。您应该首先查看备选方案,例如更高级别的功能,看看它们是否能更好地满足您的需求。

来自Alternatives to exec/eval?

  

使用字符串

中的名称设置和获取变量的值      

[while eval]会起作用,通常不建议使用对程序本身有意义的变量名称。

     

相反,最好使用字典。

这不是惯用的

来自http://lucumr.pocoo.org/2011/2/1/exec-in-python/(强调我的)

  

Python不是PHP

     

不要试图绕过Python习语,因为其他一些语言的表达方式不同。命名空间在Python中是有原因的,只是因为它为您提供了工具exec并不意味着您应该使用该工具。

很危险

来自http://nedbatchelder.com/blog/201206/eval_really_is_dangerous.html(强调我的)

  

因此,即使删除所有全局变量和内置函数,eval也不安全!

     

所有这些尝试保护eval()的问题在于它们是黑名单。他们明确地删除可能有危险的东西。这是一场失败的战斗,因为如果只有一个项目不在列表中,你可以攻击系统

     

那么,eval可以安全吗?很难说。在这一点上,我最好的猜测是,如果你不能使用任何双下划线,你就不会有任何伤害,所以如果你排除任何带有双下划线的字符串,你就是安全的。也许...

很难阅读和理解

来自http://stupidpythonideas.blogspot.it/2013/05/why-evalexec-is-bad.html(强调我的):

  

首先, exec让人类更难阅读您的代码。为了弄清楚发生了什么,我不必阅读你的代码,我必须阅读你的代码,找出它将要生成的字符串,然后阅读那个虚拟代码。因此,如果您正在团队工作,或者发布开源软件,或者在StackOverflow等地方寻求帮助,那么您就会让其他人更难帮助您。如果您有可能在6个月后调试或扩展此代码,那么您就会直接让自己变得更难。

答案 7 :(得分:4)

结帐eval

x = 1
print eval('x+1')
->2

答案 8 :(得分:3)

使用eval

答案 9 :(得分:3)

最合乎逻辑的解决方案是使用内置的eval()函数。另一种解决方案是将该字符串写入临时python文件并执行它。

答案 10 :(得分:2)

值得一提的是,&#39;如果你想调用一个python文件,那么exec的兄弟就像execfile一样存在。如果您正在使用包含可怕IDE的第三方软件包并且您希望在其软件包之外进行编码,那么这有时会很好。

示例:

execfile('/path/to/source.py)'

或:

exec(open("/path/to/source.py").read())

答案 11 :(得分:2)

我尝试了很多事情,但是唯一起作用的是以下内容:

temp_dict = {}
exec("temp_dict['val'] = 10") 
print(temp_dict['val'])

输出:

10

答案 12 :(得分:1)

正如其他人所提到的,它是“ exec” ..

但是,如果您的代码包含变量,则可以使用“全局”来访问它,还可以防止编译器引发以下错误:

  

NameError:名称'p_variable'未定义

exec('p_variable = [1,2,3,4]')
global p_variable
print(p_variable)

答案 13 :(得分:0)

好的..我知道这不是一个完全正确的答案,但可能是一个注意事项,让人们像我一样看着这个。我想为不同的用户/客户执行特定的代码,但也想避免exec / eval。我最初希望将代码存储在每个用户的数据库中并执行上述操作。

我最终在&#39; customer_filters&#39;中创建了文件系统上的文件。文件夹并使用&#39; imp&#39;模块,如果没有为该客户申请过滤器,则只进行

import imp


def get_customer_module(customerName='default', name='filter'):
    lm = None
    try:
        module_name = customerName+"_"+name;
        m = imp.find_module(module_name, ['customer_filters'])
        lm = imp.load_module(module_name, m[0], m[1], m[2])
    except:
        ''
        #ignore, if no module is found, 
    return lm

m = get_customer_module(customerName, "filter")
if m is not None:
    m.apply_address_filter(myobj)

所以customerName =&#34; jj&#34; 将从customer_filters \ jj_filter.py文件中执行apply_address_filter