Python 中的 *args 和 **kwargs。
这两个是 Python 中非常强大的特性,它们主要用于函数定义,允许你向函数传递可变数量的参数。
1. *args(非关键字可变参数)
*args 用于接收任意数量的非关键字参数( positional arguments),并将其放入一个元组(tuple) 中。
*是解包操作符。args只是一个约定俗成的名字,你可以使用任何你喜欢的名字(例如*vars),但使用*args是最佳实践,能让代码更易读。
何时使用?
当你不确定函数会接收多少个非关键字参数时。
示例:
def sum_numbers(*args):
print(f"接收到的参数(元组): {args}")
total = 0
for num in args:
total += num
return total
# 调用函数
result1 = sum_numbers(1, 2)
print(result1) # 输出: 接收到的参数(元组): (1, 2) \n 3
result2 = sum_numbers(10, 20, 30, 40, 50)
print(result2) # 输出: 接收到的参数(元组): (10, 20, 30, 40, 50) \n 150
# 甚至可以没有参数
result3 = sum_numbers()
print(result3) # 输出: 接收到的参数(元组): () \n 0
另一个重要用途:解包列表/元组
你可以在函数调用时使用 * 来将一个列表或元组解包成一串独立的参数传入函数。
def my_function(a, b, c):
print(a, b, c)
my_list = [1, 2, 3]
my_tuple = (4, 5, 6)
# 不使用 *,整个列表会被当作一个参数 a
# my_function(my_list) 这会报错,因为 b 和 c 缺少参数
# 使用 * 解包
my_function(*my_list) # 输出: 1 2 3
my_function(*my_tuple) # 输出: 4 5 6
2. **kwargs(关键字可变参数)
**kwargs 用于接收任意数量的关键字参数( keyword arguments),并将其放入一个字典(dictionary) 中。
**是解包操作符,用于键值对。kwargs同样是约定俗成的名字,意思是 "keyword arguments"。
何时使用?
当你不确定函数会接收多少个关键字参数时。
示例:
def introduce_yourself(**kwargs):
print(f"接收到的参数(字典): {kwargs}")
for key, value in kwargs.items():
print(f"{key}: {value}")
# 调用函数
introduce_yourself(name="Alice", age=30, job="Engineer")
# 输出:
# 接收到的参数(字典): {'name': 'Alice', 'age': 30, 'job': 'Engineer'}
# name: Alice
# age: 30
# job: Engineer
introduce_yourself(country="Japan", language="Japanese")
# 输出:
# 接收到的参数(字典): {'country': 'Japan', 'language': 'Japanese'}
# country: Japan
# language: Japanese
另一个重要用途:解包字典
你可以在函数调用时使用 ** 来将一个字典解包成关键字参数传入函数。
def greet_person(name, message):
print(f"Hello {name}, {message}")
my_dict = {'name': 'Bob', 'message': 'how are you?'}
# 使用 ** 解包字典
greet_person(**my_dict) # 输出: Hello Bob, how are you?
# 这等价于:
# greet_person(name='Bob', message='how are you?')
3. 组合使用:标准参数顺序
在定义一个函数时,如果需要同时使用多种参数,它们必须遵循严格的顺序:
标准顺序:(普通参数, *args, 关键字参数, **kwargs)
def complex_function(a, b, *args, default_param="Hi", **kwargs):
print(f"a: {a}")
print(f"b: {b}")
print(f"args: {args}")
print(f"default_param: {default_param}")
print(f"kwargs: {kwargs}")
# 调用示例
complex_function(1, 2, 3, 4, 5, default_param="Hello", x=10, y=20, z=30)
输出:
a: 1
b: 2
args: (3, 4, 5) # 3,4,5 被 *args 捕获
default_param: Hello # 明确指定的关键字参数
kwargs: {'x': 10, 'y': 20, 'z': 30} # 其他关键字参数被 **kwargs 捕获
错误示例:
将 *args 放在 **kwargs 后面是不允许的,会引发语法错误。
def wrong_function(a, **kwargs, *args): # SyntaxError: invalid syntax
...
总结
| 特性 | 语法 | 捕获内容 | 数据类型 | 主要用途 |
|---|---|---|---|---|
| 非关键字可变参数 | *args | 多余的非关键字参数 | 元组 (Tuple) | 1. 函数定义:接收任意数量参数 2. 函数调用:解包序列 |
| 关键字可变参数 | **kwargs | 多余的关键字参数 | 字典 (Dictionary) | 1. 函数定义:接收任意数量关键字参数 2. 函数调用:解包字典 |
掌握 *args 和 **kwargs 可以让你编写出非常灵活和通用的函数,是 Python 函数高级用法的基础。