Python不定长参数 (*args、**kwargs含义),附使用范例

您所在的位置:网站首页 数码相机照片导出 Python不定长参数 (*args、**kwargs含义),附使用范例

Python不定长参数 (*args、**kwargs含义),附使用范例

2024-07-16 15:10:43| 来源: 网络整理| 查看: 265

目录概要五种函数参数类型对比表接受任意多个参数的函数定义方法混合定义时注意事项1 函数参数类型1.1 POSITIONAL_ONLY 位置参数1.2 POSITIONAL_OR_KEYWORD 位置或关键字参数1.3 VAR_POSITIONAL 可变长参数1.4 KEYWORD_ONLY 关键字参数1.5 VAR_KEYWORD 可变关键字参数2. 函数参数传递形式2.1 VAR_POSITIONAL 可变长参数 参数传递2.2 VAR_KEYWORD 可变关键字参数 参数传递2.3 命名关键字参数 参数传递案例:遍历文件夹中文件 本片文章主要整合15. 函数和装饰器和python的可变参数和关键字参数(*args **kw)两篇文章,并做对比总结,以及添加综合案例。主要目标是熟悉 python 中函数传参种类和方法,并掌握不同传参的优缺点和联合传参的注意事项。 本文难免有不足之处,若对该主题感兴趣,如下的几个参考文献可能帮助到你

python 3.10.4 函数定义详解部分 Python 的函数是怎么传递参数的? 概要 五种函数参数类型对比表 种类 函数定义 参数传递 功能 参考 POSITIONAL_ONLY 位置参数 ord(c, /) 一些内置函数,只支持位置传入 1.1 POSITIONAL_ONLY 位置参数 POSITIONAL_OR_KEYWORD 位置或关键字参数 def foo(n): 自定义函数支持位置和关键字传入,这种类型最常见 基础传入方式,最常用 VAR_POSITIONAL 可变长参数 def variable_args(name="default", *args): 1. 传入列表 list2. 传入元组 tuple 3. 传入逐个传入元素 降低变长数组和元组传入的复杂度 2.1 VAR_POSITIONAL 可变长参数 参数传递 KEYWORD_ONLY 关键字参数 def person(name, age, *, city, job): 1. city 和 job 通过关键字传入 限制输入的关键字参数 2.3命名关键字参数 VAR_KEYWORD 可变关键字参数 def person(name, age, **kw) 1. 关键字传入2. 传入字典 dict 任意不受限,但是函数内部要增加检查 2.3VAR_KEYWORD 可变关键字参数 参数传递 接受任意多个参数的函数定义方法

定义一个可以处理任意类型任意参数数目的函数。

def test_args(*args, **kwargs): print(args) print(kwargs) test_args(1, 2, {"key0": "val0"}, name="name", age=18) >>> (1, 2, {'key0': 'val0'}) {'name': 'name', 'age': 18}

test_args() 是一个可以接受任意多个参数的函数。由于参数处理是有优先级的,kwargs 和 args 顺序不可颠倒。

混合定义时注意事项 参数定义的顺序必须是:必选参数、默认参数、可变参数/命名关键字参数和关键字参数。 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) >>> f1(1, 2) a = 1 b = 2 c = 0 args = () kw = {} >>> f1(1, 2, c=3) a = 1 b = 2 c = 3 args = () kw = {} >>> f1(1, 2, 3, 'a', 'b') a = 1 b = 2 c = 3 args = ('a', 'b') kw = {} >>> f1(1, 2, 3, 'a', 'b', x=99) a = 1 b = 2 c = 3 args = ('a', 'b') kw = {'x': 99} >>> f2(1, 2, d=99, ext=None) a = 1 b = 2 c = 0 d = 99 kw = {'ext': None} >>> args = (1, 2, 3, 4) >>> kw = {'d': 99, 'x': '#'} >>> f1(*args, **kw) a = 1 b = 2 c = 3 args = () kw = {'d': 99, 'x': '#'} >>> args = (1, 2, 3) >>> kw = {'d': 88, 'x': '#'} >>> f2(*args, **kw) a = 1 b = 2 c = 3 d = 88 kw = {'x': '#'} 1 函数参数类型

Python 中的函数参数类型一共有五种,参考 inspect 模块 ,分别是:

POSITIONAL_ONLY 位置参数,内置函数或模块使用,用户无法自定义一个只支持位置参数的函数。 POSITIONAL_OR_KEYWORD 位置或关键字参数,参数同时支持位置或者关键字传递给函数。 VAR_POSITIONAL 可变长参数,任意多个位置参数通过元组传递给函数。 KEYWORD_ONLY 关键字参数,也被称为命名参数,通过指定的键值对传递给函数。 VAR_KEYWORD 可变关键字参数,任意多个键值对参数通过字典传递给函数。 1.1 POSITIONAL_ONLY 位置参数

一些内置函数,无法通过名称来传递,否则会报不支持关键参数的错误,比如内置函数 oct(x),ord(c),divmod(x, y)等等。它们的函数手册里一般就使用一个字母来表示一个参数,常用的比如 x,y,c。

ord(c, /) Return the Unicode code point for a one-character string. ord(c='1') >>> ord(c='1') TypeError: ord() takes no keyword arguments 1.2 POSITIONAL_OR_KEYWORD 位置或关键字参数 def foo(n): print(n) foo(1) foo(n = 2) >>> 1 2

自定义的函数 foo(),不仅可以通过第一个参数位置来传递实参 1,还可以通过名称 n 来传递参数 2。这里的 n 就是一个位置或关键字参数。它是最常用的参数传递方式。

1.3 VAR_POSITIONAL 可变长参数

可变参数用一个 * 号来声明,它把所有接收到的,未被位置或关键字参数处理的参数放入一个元组。

def variable_args(name="default", *args): print("name: %s" % name) print(args) variable_args("John", "Teacher", {"Level": 1}) >>> name: john ('Teacher', {'Level': 1})

可以看到,”John” 均通过参数位置传递给了形参 name,后边多余的参数全部传递给了 *args,它是一个元组。注意键值对参数不能被它处理。

1.4 KEYWORD_ONLY 关键字参数 def keyword_only_args(name="default", *args, age): print("name: %s, age: %d" % (name, age)) print(args) keyword_only_args("John", "Teacher", {"Level": 1}, age=30) >>> name: John, age: 30 ('Teacher', {'Level': 1})

由于 age 形参位于可变参数之后,那么它的位置是不明确的,此时只能指定关键字 age,以键值对的方式传递它,被称为关键字参数。此时 args 元组中不会处理它。

命名关键字参数 是【KEYWORD_ONLY 关键字参数】的变种,详细讨论见 2.3命名关键字参数

1.5 VAR_KEYWORD 可变关键字参数

可变关键字参数通过前缀 ** 来声明,这种参数类型可以接收 0 个或多个键值对参数,并存入一个字典。

def keyword_variable_args(name="default", *args, age, **kwargs): print("name: %s, age: %d" % (name, age)) print(args) print(kwargs) keyword_variable_args("John", "Teacher", {"Level": 1}, id="332211", city="New York", age=30) >>> name: John, age: 30 ('Teacher', {'Level': 1}) {'id': '332211', 'city': 'New York'}

通过以上的示例,我们看到参数处理是有优先级的,首先通过位置匹配,然后进行关键字匹配,最后剩下的所有参数按照是否提供参数名来对应到可变参数或可变关键字参数。

2. 函数参数传递形式

在介绍了 Python 参数类型后,我们可以通过两种形式为形参提供实参。

def test_input_args(list0, num0, name="Tom"): print("list:%s, num:%d, name:%s" % (str(list0), num0, name)) test_input_args([1], 2, name="John") test_input_args(*([1], 2), **{"name": "John"}) >>> list:[1], num:2, name:John list:[1], num:2, name:John

可以通过常用位置和关键字传递,也可以使用可变参数和可变关键字参数传递,它们是等价的。有了第二种参数传递形式,就可以在一个函数中调用不同的函数了,这一特性对于实现装饰器函数非常重要。

def func0(n): print("from %s, %d" %(func0.__name__, n)) def func1(m, n): print("from %s, %d" %(func0.__name__, m + n)) def test_call_func(func, *args, **kwargs): func(*args, **kwargs) test_call_func(func0, 1) test_call_func(func1, 1, 2) >>> from func0, 1 from func0, 3 2.1 VAR_POSITIONAL 可变长参数 参数传递 # 定义函数 def calc(*numbers): sum = 0 for n in numbers: sum = sum + n * n return sum # 调用函数 - 可以传入任意个参数,包括0个参数 calc(1, 2) calc() # 调用函数 - 已经有一个 list 或者 tuple,在list或tuple前面加一个*号,把list或tuple的元素变成可变参数传进去 nums = [1, 2, 3] calc(*nums) # 传入的是nums。在函数内部会转化为 tuple 来操作

可变参数允许你传入0个或任意个参数,这些可变参数在函数调用时自动组装为一个tuple

2.2 VAR_KEYWORD 可变关键字参数 参数传递 # 定义函数 def person(name, age, **kw): print('name:', name, 'age:', age, 'other:', kw) # 传入参数 传入关键字 >>> person('Michael', 30) name: Michael age: 30 other: {} >>> person('Bob', 35, city='Beijing') name: Bob age: 35 other: {'city': 'Beijing'} >>> person('Adam', 45, gender='M', job='Engineer') name: Adam age: 45 other: {'gender': 'M', 'job': 'Engineer'} # 传入参数 已经有一个 dict >>> extra = {'city': 'Beijing', 'job': 'Engineer'} >>> person('Jack', 24, **extra) name: Jack age: 24 other: {'city': 'Beijing', 'job': 'Engineer'} # 注意kw获得的dict是extra的一份拷贝,对kw的改动不会影响到函数外的extra

关键字参数允许你传入0个或任意个含参数名的参数,这些关键字参数在函数内部自动组装为一个dict。

2.3 命名关键字参数 参数传递

对于关键字参数,函数的调用者可以传入任意不受限制的关键字参数。至于到底传入了哪些,就需要在函数内部通过kw检查。 仍以person()函数为例,我们希望检查是否有city和job参数:

def person(name, age, **kw): if 'city' in kw: # 有city参数 pass if 'job' in kw: # 有job参数 pass print('name:', name, 'age:', age, 'other:', kw)

函数内部检查关键字参数和变长参数数目,以匹配不同处理分支

def test_var_args(*args): if len(args) == 2: print(args[0]+args[1]) else: print(args[0]) test_var_args(1,2) test_var_args(1) def test_var_kwargs(**kwargs): #定义函数知道key:one two if len(kwargs) == 2: print(kwargs['one']+kwargs['two']) else: print(kwargs['one']) test_var_kwargs(one = 1, two = 2) test_var_kwargs(one = 1)

如果要限制关键字参数的名字,就可以用命名关键字参数,和关键字参数**kw不同,命名关键字参数需要一个特殊分隔符,后面的参数被视为命名关键字参数。因为加 * 后,后面参数无法通过位置传入参数,为关键字参数。例如,只接收city和job作为关键字参数。这种方式定义的函数如下:

# 定义函数 def person(name, age, *, city, job): print(name, age, city, job) # 传入参数 >>> person('Jack', 24, city='Beijing', job='Engineer') Jack 24 Beijing Engineer # 如果没有传入参数名,调用将报错 >>> person('Jack', 24, 'Beijing', 'Engineer') Traceback (most recent call last): File "", line 1, in TypeError: person() takes 2 positional arguments but 4 were given # 命名关键字带有默认值,可以简化调用 def person(name, age, *, city='Beijing', job): print(name, age, city, job) # 函数调用 >>> person('Jack', 24, job='Engineer') Jack 24 Beijing Engineer 案例:遍历文件夹中文件


【本文地址】

公司简介

联系我们

今日新闻


点击排行

实验室常用的仪器、试剂和
说到实验室常用到的东西,主要就分为仪器、试剂和耗
不用再找了,全球10大实验
01、赛默飞世尔科技(热电)Thermo Fisher Scientif
三代水柜的量产巅峰T-72坦
作者:寞寒最近,西边闹腾挺大,本来小寞以为忙完这
通风柜跟实验室通风系统有
说到通风柜跟实验室通风,不少人都纠结二者到底是不
集消毒杀菌、烘干收纳为一
厨房是家里细菌较多的地方,潮湿的环境、没有完全密
实验室设备之全钢实验台如
全钢实验台是实验室家具中较为重要的家具之一,很多

推荐新闻


图片新闻

实验室药品柜的特性有哪些
实验室药品柜是实验室家具的重要组成部分之一,主要
小学科学实验中有哪些教学
计算机 计算器 一般 打孔器 打气筒 仪器车 显微镜
实验室各种仪器原理动图讲
1.紫外分光光谱UV分析原理:吸收紫外光能量,引起分
高中化学常见仪器及实验装
1、可加热仪器:2、计量仪器:(1)仪器A的名称:量
微生物操作主要设备和器具
今天盘点一下微生物操作主要设备和器具,别嫌我啰嗦
浅谈通风柜使用基本常识
 众所周知,通风柜功能中最主要的就是排气功能。在

专题文章

    CopyRight 2018-2019 实验室设备网 版权所有 win10的实时保护怎么永久关闭