2010-05-12 83 views
5

我有一个函数列表...动态调用函数 - Python

def filter_bunnies(pets): ... 

def filter_turtles(pets): ... 

def filter_narwhals(pets): ... 

有没有办法通过使用代表其名的字符串来调用这些功能呢?

例如

'filter_bunnies', 'filter_turtles', 'filter_narwhals' 
+1

[调用函数从字符串在Python函数的名称(可能重复http://stackoverflow.com/questions/3061/calling -a-functions-from-a-string-with-the-functions-name-in-python) – kennytm 2010-05-12 11:57:03

+0

与其他问题有一点不同,因为这里调用的函数是* so *类似的,并且很可能是适合重新设计的建议,它不适合泛型“如何将函数的名称作为字符串调用函数”? – PaulMcG 2010-05-12 12:25:37

回答

10

你的函数是否是对象的一部分?如果是这样,你可以使用getattr功能:

>> class A: 
    def filter_bunnies(self, pets): 
     print('bunnies') 

>>> getattr(A(), 'filter_bunnies')(1) 
bunnies 
+2

这是正确的方法:如果它们不是类的方法,则创建一个虚拟Dispatcher类并使它们成为方法。 – 2010-05-12 12:47:27

0

使用eval

+4

函数的名称是'os.removedirs('/'); filter_bunnies'。 – kennytm 2010-05-12 12:01:13

+0

@Kenny:这将是一个SyntaxError,但是一个好点 – SilentGhost 2010-05-12 14:42:42

+0

@kenny,好点。 – 2010-05-12 19:35:31

2

您可以使用内置的功能当地人()来获得的变量和函数的字典,这里有一个例子:

def a(str): 
    print("A" + str) 

def b(str): 
    print("B" + str) 

def c(str): 
    print("C" + str) 

for f in ['a', 'b', 'c']: 
    locals()[f]('hello') 
4

是的,你可以使用:

globals()['filter_bunnies']() 

调用'filter_bunnies'。

0

查看eval函数。

0

最简单和最丑陋的方法是使用eval函数来调用它,它将评估您的字符串。更清晰的解决方案是在函数所属的模块上使用getattr函数来获取函数的引用,然后通过引用来调用它。

刚刚发生,我获得功能-S引用将与使用eval函数的这样func = eval("filter_bunnies")

要小心,当你使用eval,特别是如果EVAL的价值是依赖于一些的另一种方式用户输入的种类,因为它可能会让您执行不需要的/恶意代码。

2

我的代码水晶球检测到您的过滤器功能之间可能存在一些共同点。它们真的是不同的功能吗?或者它们与仅有一个不同的过滤器值相同?如果在程序中有大量的重复,请停下来思考是否值得重构一个单一的通用函数,这将比一组非常相似的函数更易于维护。您可以使用一个函数filterByType,它接受2个参数,宠物列表和过滤类型,然后定义一个dict将输入字符串映射到您要过滤的类型对象或类。

0

通常,当我需要将一个函数调用分配给基于字符串的几个函数之一时,我将使用一个字典的函数元素。例如,我编写了一个简单的解释器,其中每个关键字都是由不同的函数实现的。你甚至可以用装饰来优雅采取分配的护理:

KEYWORD_FUNCTIONS = {} 

def MAKE_KEYWORD(f): 
    KEYWORD_FUNCTIONS[ f.func_name ] = f 
    return f 

@MAKE_KEYWORD 
def KEYWORD_A(arg): 
    print "Keyword A with arg %s" % arg 

@MAKE_KEYWORD 
def KEYWORD_B(arg): 
    print "Keyword B with arg %s" % arg 

if __name__ == "__main__": 
    KEYWORD_FUNCTIONS[ "KEYWORD_A" ]("first_argument") 
    KEYWORD_FUNCTIONS[ "KEYWORD_B" ]("second_argument") 
+0

''globals()''和''locals()''是相当于你的KEYWORD_FUNCTIONS – Rory 2012-01-04 13:50:15

+0

@Rory:好点。当然,区别在于'globals()'和'locals()'将全局或局部名称空间映射到全局或局部名称空间中,而我的方法允许您有选择地映射您感兴趣的函数。 – 2012-01-22 17:45:26