Python中定义函数时可以指定函数参数类型以满足不同需要,也可以将各种类型参数组合起来使用,十分灵活。不同类型参数各有特色,如果使用恰当可以丰富函数功能,使用者调用函数时也方便很多。但用法不当时也会造成很多麻烦,得不偿失。函数参数类型及特点:

1、位置参数

      顾名思义,位置固定的参数,调用函数时需要一一对应为其赋值,不能不赋值,更不能不按设定类型赋值。

      优点:用法简单,在函数定义时按顺序列在括号里就行。

      缺点:不够灵活,必须知道每个参数类型及含义,为确保函数功能正常不得在函数中进行参数检查。

      例:

def pos_para(a,b,c,d):
    print(a,b,c,d)

2、默认参数

      有些时候函数中某些参数存在默认值,或者为了简化调用过程可以省略不写,从而使用默认值运行函数。因此可以使用默认参数,默认参数用法是直接在定义函数时对其进行赋值。调用时如果没有特殊需要可以不对其再次赋值。需要注意的是默认参数必须在位置参数(如果有)后面声明。

      优点:调用简单,没有特殊需求可以不赋值。

      缺点:由于调用时省略赋值过程,默认参数为一个空的list时需要将其内容初始化为None,即一个无效的固定值,该值无特殊含义,只是因为Python特性如果没有初始化则“悬空”,如果在函数中为该list添加了成员,此list内容会保存在新创建的list中下次再调用时又会在这个list基础上增加新成员。

例(错误用法):

def default_para(L=[]):
    L.append('endline')
    return L

例(正确用法):

def default_para(L=[None]):
    if L is None:
        L = []
    L.append('endline')

      以上两种写法的主要区别就是正确用法用无意义值None对新建的list进行初始化,函数使用这种不可变的参数很有用,可以确保多个任务同时访问时也不会出错。

3、可变参数

      可变参数也是为了简化使用过程,因为并未限制参数数量,使用起来十分灵活。可变参数的声明只需要在参数名前面加一个'*'即可,因此只需要一个参数就能实现接受多个赋值。可变参数将接收到的值存放于一个tuple中,再按照顺序进行使用。

      优点:灵活,简化使用,参数数量较多直接赋值即可。

      缺点:仍然需要检查输入类型是否符合设定。

      例:

def variable_para(*para):
    for n in para:
        print(n)

4、关键字参数

      "关键字"这个词可以让人联想到Python中的某种数据类型->dict,因此,关键字参数的作用就类似一个dict,调用时可以直接输入一个dict或者按照"key=value"的格式进行赋值。声明关键字参数时只需要在参数名前边加上"**"。

      优点:可以扩展参数,在类似赋值对象的应用场景下很便捷。

      缺点:必须按照dict的格式赋值,用途有限。不能限制输入参数。

      例:

def key_para(**kw):
    print(kw)

key_para(name='Thomas',age='18',gender='Male')

5、命名关键字参数

     命名关键字参数是为了解决关键字参数不能限制输入参数的问题,如果不对输入参数进行限制,可能出现未知问题。命名关键字参数的声明很简单,只需要用"*"将其与其他参数隔开,并且置于其他参数之后。因为有参数名限制,调用时需要按照参数类型进行赋值,就避免了不受限参数带来的问题。

     优点:限制参数范围,减少因关键字参数不受限造成的错误。

     缺点:不够灵活。

     例:

def named_key_para(a,b,*,name,age):
    print(a,b,name,age)

6、参数组合

在Python中定义函数,可以用位置参数、默认参数、可变参数、关键字参数和命名关键字参数,这5种参数都可以组合使用。但是请注意,参数定义的顺序必须是:必选参数、默认参数、可变参数、命名关键字参数和关键字参数。

例:

def f1(a, b, c=0, *args, **kw):
    print('a =', a, 'b =', b, 'c =', c, 'args =', args, 'kw =', kw)

def f2(a, b, c=0, *, d, **kw):
    print('a =', a, 'b =', b, 'c =', c, 'd =', d, 'kw =', kw)

在函数调用的时候,Python解释器自动按照参数位置和参数名把对应的参数传进去。当然,也可以将前面几个参数加入tuple,将后面几个参数做成一个dict直接进行赋值。

para1 = (1,2,3,a)
para2 = {age = '18', gender = 'Male'}
f1(*para1,**para2)

para1 = (1,2,a)
para2 = {'d':123,'age':'#'}
f2(*para1,**para2)


     虽然参数组合基本可以满足各种功能需求,但是用起来十分繁琐且容易出错,因此不建议在一个函数中使用太多组合。