调用未知的Python函数

Tei*_*ion 6 python

这是我能为这个主题提出的最佳名称,我的搜索都没有提供与该问题相关的信息.

如何从字符串中调用函数,即

functions_to_call = ["func_1", "func_2", "func_3"]

for f in functions_to_call:
    call f
Run Code Online (Sandbox Code Playgroud)

Ant*_*wns 19

您可以使用python builtin locals()来获取本地声明,例如:

def f():
    print "Hello, world"

def g():
    print "Goodbye, world"

for fname in ["f", "g"]:
    fn = locals()[fname]
    print "Calling %s" % (fname)
    fn()
Run Code Online (Sandbox Code Playgroud)

您可以使用"imp"模块从用户指定的python文件加载函数,这样可以提供更多的灵活性.

使用locals()确保你不能调用泛型python,而使用eval,你可能最终会让用户将你的字符串设置为类似的东西:

f = 'open("/etc/passwd").readlines'
print eval(f+"()")
Run Code Online (Sandbox Code Playgroud)

或类似的,最终你的编程做你不希望的事情.使用locals()和dicts的类似技巧一般只会给攻击者KeyErrors.


nos*_*klo 15

你怎么不知道要调用的函数的名称?存储函数而不是名称:

functions_to_call = [int, str, float]

value = 33.5

for function in functions_to_call:
    print "calling", function
    print "result:", function(value)
Run Code Online (Sandbox Code Playgroud)


LB4*_*B40 8

类似的东西...当我在python中查看函数指针时..

def myfunc(x):
    print x

dict = {
    "myfunc": myfunc
}

dict["myfunc"]("hello")

func = dict.get("myfunc")
if callable(func):
    func(10)
Run Code Online (Sandbox Code Playgroud)

  • +1表示这个想法(这也允许将可调用的内容限制为特定的集合),但虚拟-1表示调用字典“dict”,这将隐藏本地范围中的类型名称...... (2认同)

mar*_*cog 6

看看getattr函数:

http://docs.python.org/library/functions.html?highlight=getattr#getattr

import sys

functions_to_call = ["func_1", "func_2", "func_3"]

for f in functions_to_call:
  getattr(sys.modules[__name__], f)()
Run Code Online (Sandbox Code Playgroud)


Chr*_*rch 2

functions_to_call = ["func_1", "func_2", "func_3"]

for f in functions_to_call:
    eval(f+'()')
Run Code Online (Sandbox Code Playgroud)

编辑添加:

是的,eval() 通常是一个坏主意,但这正是OP 正在寻找的。

  • 的确。没有理由在这里使用 eval();`locals()[f]()` 就可以了。这仍然是一种非常值得怀疑的方法,但比 eval() 好得多。 (2认同)