在python中使用参数列表调用函数

时间:2009-05-03 13:43:34

标签: python function

我正在尝试在python中调用另一个函数内的函数,但找不到正确的语法。我想做的是这样的事情:

def wrapper(func, args):
    func(args)

def func1(x):
    print(x)

def func2(x, y, z):
    return x+y+z

wrapper(func1, [x])
wrapper(func2, [x, y, z])

在这种情况下,第一个呼叫将起作用,第二个呼叫不起作用。 我想要修改的是包装函数,而不是被调用的函数。

6 个答案:

答案 0 :(得分:250)

稍微扩展其他答案:

在行中:

def wrapper(func, *args):

args旁边的*表示“获取给定的其余参数并将其放入名为args的列表中”。

在行中:

    func(*args)

此处args旁边的*表示“将此列表称为args并将其'展开'到其余参数中。

所以你可以做到以下几点:

def wrapper1(func, *args): # with star
    func(*args)

def wrapper2(func, args): # without star
    func(*args)

def func2(x, y, z):
    print x+y+z

wrapper1(func2, 1, 2, 3)
wrapper2(func2, [1, 2, 3])

wrapper2中,列表会显式传递,但在两个包装器args中都包含列表[1,2,3]

答案 1 :(得分:17)

包装函数的最简单方法

    func(*args, **kwargs)

...是手动编写一个可以在其内部调用 func()的包装器:

    def wrapper(*args, **kwargs):
        # do something before
        try:
            return func(*a, **kwargs)
        finally:
            # do something after

在Python中,函数是一个对象,因此您可以将其名称作为另一个函数的参数传递并返回。您还可以为任何函数 anyFunc()

编写包装器生成器
    def wrapperGenerator(anyFunc, *args, **kwargs):
        def wrapper(*args, **kwargs):
            try:
                # do something before
                return anyFunc(*args, **kwargs)
            finally:
                #do something after
        return wrapper

请注意,在Python中,当您不知道或不想命名函数的所有参数时,您可以引用一个参数元组,该元组由其名称表示,前面带有星号。函数名后的括号:

    *args

例如,您可以定义一个可以接受任意数量参数的函数:

    def testFunc(*args):
        print args    # prints the tuple of arguments

Python提供了对函数参数的进一步操作。您可以允许函数获取关键字参数。在函数体内,关键字参数保存在字典中。在函数名称后的括号中,此字典由两个星号表示,后跟字典名称:

    **kwargs

打印关键字参数字典的类似示例:

    def testFunc(**kwargs):
        print kwargs    # prints the dictionary of keyword arguments

答案 2 :(得分:10)

您可以将* args和** kwargs语法用于可变长度参数。

What do *args and **kwargs mean?

来自官方的python教程

http://docs.python.org/dev/tutorial/controlflow.html#more-on-defining-functions

答案 3 :(得分:9)

您的问题的字面答案(完全按照您的要求进行操作,只更改包装器,而不是函数或函数调用)只是改变行

func(args)

阅读

func(*args)

这告诉Python采用给定的列表(在本例中为args)并将其内容作为位置参数传递给函数。

这个技巧适用于函数调用的两个“边”,因此定义如下函数:

def func2(*args):
    return sum(args)

可以接受与你抛出的位置参数一样多的数据,并将它们全部放入名为args的列表中。

我希望这有助于澄清一些事情。请注意,使用**代替*也可以使用dicts / keyword参数。

答案 4 :(得分:8)

你需要使用参数解包..

def wrapper(func, *args):
    func(*args)

def func1(x):
    print(x)

def func2(x, y, z):
    print x+y+z

wrapper(func1, 1)
wrapper(func2, 1, 2, 3)

答案 5 :(得分:0)

以前答案的一小部分,因为我无法找到问题的解决方案,这不值得开一个新问题,但在此引导我。

这是一个小代码段,它结合了listszip()*args,以提供一个包装器,可以使用未知数量的参数处理未知数量的函数。

def f1(var1, var2, var3):
    print(var1+var2+var3)

def f2(var1, var2):
    print(var1*var2)

def f3():
    print('f3, empty')

def wrapper(a,b, func_list, arg_list):
    print(a)
    for f,var in zip(func_list,arg_list):
        f(*var)
    print(b)

f_list = [f1, f2, f3]
a_list = [[1,2,3], [4,5], []]

wrapper('begin', 'end', f_list, a_list)

请注意,zip()未对长度不等的列表提供安全检查,请参阅zip iterators asserting for equal length in python