第 5 章 函数
5.1 定义与调用
def greet(name):
"""向指定的人问好。(这是 docstring 文档字符串)"""
return f"Hello, {name}!"
greet("Alice")
help(greet)
def 定义,函数名约定 snake_case;
return 返回结果并结束函数;没有 return 或裸 return 返回 None;
return a, b 实际返回一个元组,可解包接收;
函数是一等对象:可以赋值给变量、当参数传递、放进列表/字典。
5.2 参数详解(重点)
位置参数与关键字参数
def intro(name, age):
print(f"{name},{age} 岁")
intro("Alice", 25)
intro(age=25, name="Alice")
intro("Alice", age=25)
默认参数
def power(x, n=2):
return x ** n
power(3)
power(3, 3)
黄金规则:默认值必须是不可变对象(None、数字、字符串等)。可变默认值的坑见第 3 章 3.6 节——默认参数在函数定义时只求值一次,之后所有调用共享。
可变参数:*args 与 **kwargs
def demo(a, *args, **kwargs):
print(a)
print(args)
print(kwargs)
demo(1, 2, 3, x=4)
调用端的 * / ** 是解包:
nums = [1, 2, 3]
print(*nums)
d = {"name": "Alice", "age": 25}
intro(**d)
参数定义顺序与强制规则
完整顺序:位置参数 → 默认参数 → *args → 仅关键字参数 → **kwargs
def f(pos, default=1, *args, kw_only, **kwargs): ...
def create_user(name, /, *, password):
...
create_user("alice", password="123")
create_user(name="alice", password="123")
5.3 作用域:LEGB 规则
变量查找顺序:Local(函数内)→ Enclosing(外层函数)→ Global(模块级)→ Built-in(内置)。
x = "global"
def outer():
x = "enclosing"
def inner():
x = "local"
print(x)
inner()
def counter():
count = 0
def inc():
nonlocal count
count += 1
return count
return inc
c = counter()
c(); c()
5.4 匿名函数 lambda
lambda 的真正用武之地是高阶函数的实参:
pairs = [(1, "one"), (4, "four"), (2, "two")]
sorted(pairs, key=lambda p: p[1])
users = [{"name": "B", "age": 20}, {"name": "A", "age": 30}]
max(users, key=lambda u: u["age"])
list(map(lambda x: x * 2, [1, 2, 3]))
list(filter(lambda x: x > 1, [1, 2, 3]))
风格建议:能写 def 就别赋值 lambda(PEP 8);简单场景优先用推导式替代 map/filter。
5.5 常用内置高阶函数
nums = [3, 1, 4, 1, 5]
sorted(nums, reverse=True)
sum(nums); max(nums); min(nums)
list(map(str, nums))
list(filter(None, [0, 1, "", "a"]))
any(x > 3 for x in nums)
all(x > 0 for x in nums)
5.6 类型提示(Type Hints)
Python 是动态类型,但可以标注类型,提升可读性并支持工具检查(mypy / IDE):
def repeat(text: str, times: int = 2) -> str:
return text * times
def process(items: list[str]) -> dict[str, int]:
return {item: len(item) for item in items}
repeat(3, "x")
常见标注:int、float、str、bool、list[X]、dict[K, V]、X | None(3.10+ 表示可空)。
5.7 装饰器(入门)
装饰器是"接收函数、返回函数"的高阶函数,用 @ 语法给函数包一层:
import time
import functools
def timer(func):
@functools.wraps(func)
def wrapper(*args, **kwargs):
start = time.perf_counter()
result = func(*args, **kwargs)
print(f"{func.__name__} 耗时 {time.perf_counter() - start:.4f}s")
return result
return wrapper
@timer
def slow_sum():
return sum(range(10_000_000))
slow_sum()
等价于 slow_sum = timer(slow_sum)。常见内置/标准库装饰器:@staticmethod、@classmethod、@property(见第 6 章)、@functools.cache。
5.8 本章小结
参数规则:默认值用不可变对象;*args/**kwargs 收集与解包是一对;
作用域按 LEGB 查找;改外层变量需要 nonlocal/global;
lambda 只做单表达式;类型提示是给人看的契约;
装饰器 = 函数包函数,@functools.wraps 别忘加。
下一章:面向对象——类、继承与魔术方法。