Python使用字典键作为函数名

时间:2015-04-23 19:15:19

标签: python

我希望能够使用字典键作为函数名称,但我不确定它是否可行。作为一个简单示例,我想要class().dothis(dictkey, otherstuff)选项,而不是class().dictkey(otherstuff)。这是一个无法运行的代码示例,用于了解我的想法。

class testclass:
    def __init__(self):
        self.dict = {'stuff':'value', 'stuff2':'value2'}

    #I know this part won't work, but it gives the general idea of what I'd like to do
    for key, value in self.dict.iteritems():
        def key():
            #do stuff
            return value

>>> testclass().stuff()
'value'

显然每个密钥都需要检查它是否重要,但除此之外,如果可以开始工作,我会感激一些帮助。

基本上,我的脚本是将其他脚本存储在Maya场景文件的标题中,因此您可以调用命令并执行匹配的脚本。它以文本格式将脚本存储在字典中,在那里我做了一个类似包装的东西,这样你可以毫不费力地输入args和kwargs,并且因为你只能亲自输入和执行脚本,所以几乎没有任何危险恶意,除非你自己做。

列表被pickle和base64编码,因为它需要以字符串格式为标题,因此每次调用该函数时它都会对字典进行解码,以便您可以编辑或读取它,所以理想情况下我需要这些函数每次调用它时都会构建。

来自run函数的几个例子:

    Execute a simple line of code
    >>> SceneScript().add("MyScript", "print 5")
    >>> SceneScript().run("MyScript")
    5

    Execute a function with a return
    >>> SceneScript().add("MyScript", "def test(x): return x*5")
    >>> SceneScript().run("MyScript", "test(10)", "test('c')")
    [50, 'ccccc']

    Pass a variable to a function command
    >>> SceneScript().run("MyScript", 'test(a+b)', a=10, b=-50)
    [-200]

    Execute a function without a return
    >>> SceneScript().add("MyScript", "def test(x): print x*5")
    >>> SceneScript().run("MyScript", "test(10)", "test('c')")
    50
    ccccc
    [None, None]

    Pass a variable
    >>> SceneScript().add("MyScript", "print x")
    >>> SceneScript().run("MyScript", x=20)
    20

正如这个问题所要求的那样,就上述代码而言,我希望有类似SceneScript().MyScript( "test(10)" )之类的东西,只是为了让它更容易使用。

3 个答案:

答案 0 :(得分:2)

我能想到的唯一“正确”方式是这样的:

class SomeClass(object):
    def __init__(self, *args, **kwargs):
        funcs = {'funcname': 'returnvalue', ...}
        for func, ret_val in funcs.iteritems():
            setattr(self, func, self.make_function(ret_val))

    @staticmethod
    def make_function(return_value):
        def wrapped_function(*args, **kwargs):
            # do some stuff
            return return_value
        return wrapped_function

这应该允许你这样做:

>>> foo = SomeClass()
>>> foo.funcname()
'returnvalue'

当然为什么你想做这样的事情的问题仍然没有答案:)

每个更新的问题

编辑

问题在于您无法将方法安全地分配给函数签名。我不确定SceneScript().add当前是如何工作的,但这基本上不得不以某种方式与此相关。

答案 1 :(得分:0)

您是否正在寻找通过名称字符串调用驻留在当前模块中的函数的方法?如果是的话,

def stuff(arg):
  return 5

d = {"stuff":"value","stuff2":"value2"}
print globals()["stuff"](d["stuff"])

将打印5。

答案 2 :(得分:0)

我会使用functools.partial__getattribute__

来研究部分函数
class Foo:
    def __init__(self):
        self.a = 5
        self.b = 6

    def funca(self, x):
        print(self.a + x)

    def funcb(self, x):
        self.a += x
        self.funca(x)

mydict = {'funca':1, 'funcb':2}
foo = Foo()

for funcname,param in mydict.items():
    print('foo before:', foo.a, foo.b)
    print('calling', funcname)
    functools.partial(foo.__getattribute__(funcname), param)()
    print('foo after:', foo.a, foo.b)

输出:

foo before: 5 6
calling funca
6
foo after: 5 6
foo before: 5 6
calling funcb
9
foo after: 7 6