我需要编写一个接受3个参数的方法:
string
,其名称为list
个参数。这包括具有默认值和*varargs
的参数,但不包括**kwargs
dict
,如果没有None
醇>
我需要使用此输入来检索函数并调用它。例如:
def dispatch(name, args, kwargs=None):
do_magic_here(name, args, kwargs)
def meth1():
print "meth1"
def meth2(a, b):
print "meth2: %s %s" % (a, b)
def meth3(a, **kwargs):
print "meth3: " + a
for k,v in kwargs.iteritems():
print "%s: %s" % (k,v)
我需要能够调用这样的事情:
>>> dispatch("meth1", [])
meth1
>>> dispatch("meth2", [1, 3])
meth2: 1 3
>>> dispatch("meth3", [1], {"hello":2, "there":3})
meth3: 1
hello: 2
there: 3
我可以这样做:
def do_magic_here(name, args, kwargs=None):
if name=="meth1":
meth1()
if name=="meth2":
meth2(args[0], args[1])
if name=="meth3":
meth3(args[0], **kwargs)
但是我试图像40种方法一样调度,而且这个数字可能会扩大,所以我希望有更多的编程方式来实现它。我正在寻找getattr
的东西,但我无法弄明白。
答案 0 :(得分:4)
我会用
def dispatch(name, *args, **kwargs):
func_name_dict[name](*args, **kwargs)
与
func_name_dict = {'meth1':meth1,
'meth2':meth2,
...}
允许您更自然,更透明地通过args
和kwargs
:
>>> dispatch("meth2", 1, 3)
meth2: 1 3
您当然可以使用globals()
或locals()
代替dict,但是您可能需要注意每个命名空间中您执行或不希望向调用者公开哪些函数
答案 1 :(得分:2)
确实,getattr
会帮助你。
class X:
def a(self):
print('a called')
def b(self, arg):
print('b called with ' + arg)
x = X()
getattr(x, 'a')()
# a called
getattr(x, 'b')('foo')
# b called with foo
就像getattr
以相同的方式处理方法和字段一样,您可以处理
通过引用locals()
或globals()
来与函数和变量无关的函数和变量。
如果要引用全局范围内的函数:
globals()['meth'](args)
例如:
def dispatch(name, *args, **kwargs):
globals()[name](*args, **kwargs)
dispatch('meth3', 'hello', foo='bar')
# meth3: hello
# foo: bar
请记住,在Python中,您始终可以使用**
传递参数列表或关键字参数的词典:
dispatch('meth3', *['hello'], **{'foo':'bar'})
如果您真的更喜欢将参数作为list / dict传递给dispatch
:
def dispatch(name, args, kwargs):
globals()[name](*args, **kwargs)
dispatch('meth3', ['hello'], {'foo': 'bar'})