Python核心语法——函数
在 Python 编程中函数是组织代码、实现复用、提高可读性的核心工具。无论是处理数据、控制流程还是构建复杂系统函数都扮演着不可或缺的角色。本文基于一套完整的 PPT 讲义系统梳理 Python 函数的基础用法、进阶特性及类型注解帮助读者从零到一掌握函数编程的精髓。一、函数基础1.1 什么是函数函数是组织好的、可重复使用的、用来实现特定功能的代码片段。Python 内置了大量函数例如input()、print()、max()、min()、len()、sum()等它们都是提前定义好的、可重复使用、实现特定功能的代码块。通过调用这些函数我们可以轻松完成输入输出、数值计算等常见任务而无需重复编写逻辑。1.2 函数定义与调用函数必须先定义再调用。定义时并不会执行函数体只有在调用时函数体内的逻辑才会真正运行。函数体通过缩进来描述归属关系。基本语法def 函数名(参数列表): # 函数体 return 返回值注意事项函数定义后不会自动执行必须显式调用。函数体中的代码必须缩进一致。函数名应遵循命名规范小写字母、下划线分隔。1.3 函数的参数与返回值在定义函数时可以根据业务需要指定参数和返回值。形参形式参数函数定义时括号里的参数只能在函数内部使用局部变量。实参实际参数函数调用时传入的具体值。示例def add(a, b): # a, b 为形参 return a b result add(3, 5) # 3, 5 为实参多个返回值Python 函数可以返回多个值它们会被封装到一个元组中调用时可以使用元组解包来接收。def get_min_max(data): return min(data), max(data) min_val, max_val get_min_max([1, 2, 3, 4])1.4 函数的说明文档Docstring说明文档Docstring是写在函数开头用三个引号包裹的字符串用于解释函数的功能、参数、返回值等信息方便调用者清楚函数的具体作用及细节。示例def circle_area_len(radius): 计算圆的面积和周长 Args: radius (float): 圆的半径 Returns: tuple: (面积, 周长) import math area math.pi * radius ** 2 circumference 2 * math.pi * radius return area, circumference查看说明文档的方式使用help(函数名)例如help(circle_area_len)。在 IDE如 PyCharm、VS Code中将鼠标悬浮在函数名上会自动展示文档推荐。好的文档能让你的代码更容易理解、使用和维护1.5 函数的嵌套调用嵌套调用指的是在一个函数中又调用了另外一个函数。函数调用遵循栈结构最后被调用的函数最先返回LIFO——Last In First Out后进先出。调用流程示意function_a() 开始 │ ├─ 打印 a ... before │ ├─ 调用 function_b() │ │ │ ├─ 打印 b ... before │ │ │ ├─ 调用 function_c() │ │ │ │ │ └─ 打印 c ... │ │ │ ├─ 打印 b ... after │ │ │ └─ function_b() 返回 │ ├─ 打印 a ... after │ └─ function_a() 返回这种层层调用的机制使得程序逻辑清晰但需要注意递归深度和调用栈溢出问题。1.6 案例需求1根据传入的底和高计算三角形面积面积 底 × 高 / 2。def triangle_area(base, height): 计算三角形面积 return base * height / 2 # 调用示例 print(triangle_area(5, 10)) # 输出 25.0需求2计算传入字符串中元音字母的个数元音字母为aeiouAEIOU。def count_vowels(s: str) - int: 返回字符串中元音字母的个数 vowels aeiouAEIOU count 0 for ch in s: if ch in vowels: count 1 return count # 调用示例 print(count_vowels(Hello World)) # 输出 3e, o, odef是 Python 中定义函数的关键字。count_vowels是函数名通常见名知意“计算元音”。(s: str)表示函数接受一个参数s并且通过类型注解提示s应该是一个字符串str但这只是一个提示并不会强制检查传入其他类型也能运行但可能出错。- int表示函数返回值期望是一个整数int同样只是类型提示需求3计算传入班级学员高考成绩列表中的最高分、最低分、平均分保留1位小数并返回。def score_stats(scores: list) - tuple: 返回 (最高分, 最低分, 平均分) if not scores: return None, None, None max_score max(scores) min_score min(scores) avg_score round(sum(scores) / len(scores), 1) return max_score, min_score, avg_score # 调用示例 grades [98, 76, 88, 92, 65, 79] max_s, min_s, avg_s score_stats(grades) print(f最高: {max_s}, 最低: {min_s}, 平均: {avg_s})二、函数进阶2.1 函数变量的作用域变量的作用域指的是变量在程序中可以被访问的范围。全局变量在函数外部声明的变量可以在整个模块中访问。局部变量在函数内部定义的变量只能在函数内部使用。global关键字用于明确告诉 Python 解释器在函数中要使用全局变量从而可以在函数内部修改全局变量的值。num1 10 def modify(): global num1 # 声明使用全局变量 num1 num1 20注意事项尽量避免在函数中使用全局变量因为会使代码难以维护和调试。推荐使用函数参数和返回值来传递数据而不是依赖全局变量。global主要用在程序的状态管理、配置和计数器等场景中。2.2 函数参数详解2.2.1 传参方式① 位置参数调用函数时传入实参的顺序与定义函数时形参的顺序完全一致。def calc(math, chinese, english, computer): return math chinese english computer s calc(87, 68, 92, 85) # 位置参数优点简洁缺点可读性差、易出错、维护难。适用场景参数较少不超过3个且顺序自然。② 关键字参数调用函数时以形参名作为关键字以键值的形式传递参数不要求顺序。s calc(math87, chinese68, english92, computer85)优点可读性强、易维护和扩展缺点代码稍显繁琐。适用场景参数较多或参数含义易混淆的场景。混合使用如果同时存在位置参数与关键字参数关键字参数必须在位置参数之后关键字参数之间没有顺序要求。黄金法则半年后回头看你今天写的代码能否一眼看出每个参数的含义如果不能就应该使用关键字参数。2.2.2 默认参数默认参数缺省参数在定义函数时为参数提供默认值调用时可以不传递这些参数。def greet(name, msgHello): print(f{msg}, {name}) greet(Alice) # 使用默认 msg greet(Bob, Hi) # 覆盖默认值默认参数通常放在参数列表的末尾避免歧义。2.2.3 不定长参数当参数个数不确定时可以使用不定长参数可变参数。① 位置传递*args将多个位置参数封装成一个元组tuple。def calc_data(*args): return min(args), max(args), sum(args)/len(args) min_v, max_v, avg_v calc_data(389, 39, 29, 105)② 关键字传递**kwargs将多个关键字参数封装成一个字典dict。def print_info(**kwargs): for key, value in kwargs.items(): print(f{key}: {value}) print_info(nameTom, age18, cityBeijing)应用场景*args适用于处理数量不确定的数据序列。**kwargs适用于处理数量不确定的选项或配置参数用来定制函数行为。2.2.4 参数类型函数参数可以是任何 Python 对象普通参数数字、布尔、字符串、列表、元组、集合、字典等。特殊参数函数本身即函数可以作为参数传递这为高阶函数和回调机制提供了可能。def apply(func, value): return func(value) def square(x): return x * x result apply(square, 5) # 传递函数作为参数2.3 匿名函数lambda 表达式匿名函数是没有名称的函数通过lambda表达式声明适用于简单函数的快速定义单行表达式。语法lambda 参数列表 : 函数体示例# 定义一个无参匿名函数 lambda: print(-------------------------) # 定义两个参数的加法 add lambda x, y: x y print(add(3, 5)) # 输出 8命名函数 vs 匿名函数使用匿名函数逻辑简单只在一个地方调用常作为高阶函数的参数例如sorted(iterable, keylambda x: x[1])。使用命名函数逻辑复杂需要多步操作需要多个地方重复使用或需要文档说明的场景。代码的可读性和可维护性比简洁性更重要请合理选择。2.4 案例2综合练习2.4.1 阶乘计算定义函数根据传入数字计算该数字的阶乘。分析8 的阶乘 8 × 7 × 6 × 5 × 4 × 3 × 2 × 1递推公式f(n) n × f(n-1)其中 f(1) 1。def factorial(n: int) - int: 递归计算 n 的阶乘 if n 0: raise ValueError(n 必须为非负整数) if n 0 or n 1: return 1 return n * factorial(n - 1) # 调用示例 print(factorial(5)) # 120 print(factorial(8)) # 403202.4.2 班级成绩统计根据输入的班级名称以及各个学员的考试总分统计班级的平均分以及高于平均分和低于平均分的人数。def class_stats(class_name: str, scores: list) - dict: 统计班级成绩信息 :param class_name: 班级名称 :param scores: 学员总分列表 :return: 包含统计结果的字典 if not scores: return { 班级: class_name, 平均分: None, 高于平均分人数: 0, 低于平均分人数: 0 } avg sum(scores) / len(scores) above sum(1 for s in scores if s avg) below sum(1 for s in scores if s avg) # 等于平均分的人数忽略不算高也不算低 return { 班级: class_name, 平均分: round(avg, 2), 高于平均分人数: above, 低于平均分人数: below } # 调用示例 result class_stats(高三(1)班, [580, 620, 540, 590, 610, 550]) print(result) # 输出{班级: 高三(1)班, 平均分: 581.67, 高于平均分人数: 3, 低于平均分人数: 3}2.4.3 电商订单计算器定义一个函数根据传入的商品信息商品名、价格、数量、优惠优惠券、积分抵扣和运费信息计算订单总金额。规则优惠券需要商品金额满 5000 才可使用且优惠券金额不能超过商品总价。积分抵扣需要商品总金额满 5000 才可使用100 积分抵扣 1 元抵扣金额不能超过商品总价积分只能整百抵扣。def calculate_order( items: list, # 每个元素为 (商品名, 单价, 数量) coupon: float 0.0, # 优惠券金额 points: int 0, # 可用积分 shipping: float 0.0 # 运费 ) - dict: 计算订单最终金额 :return: 包含各项明细的字典 # 计算商品总价 total_goods sum(price * qty for _, price, qty in items) # 初始折扣 discount 0.0 # 处理优惠券 if total_goods 5000 and coupon 0: discount min(coupon, total_goods) # 不能超过商品总价 # 处理积分抵扣 points_discount 0.0 if total_goods 5000 and points 100: # 整百积分每100积分抵扣1元 usable_points (points // 100) * 100 points_discount usable_points / 100 # 抵扣金额不能超过商品总价扣除优惠券后的金额 max_discount total_goods - discount if points_discount max_discount: points_discount max_discount # 最终支付金额 final_total total_goods - discount - points_discount shipping return { 商品总价: round(total_goods, 2), 优惠券抵扣: round(discount, 2), 积分抵扣: round(points_discount, 2), 运费: round(shipping, 2), 实付金额: round(final_total, 2) } # 调用示例 items [(手机, 2999, 2), (耳机, 199, 1)] # 总价 6197 result calculate_order(items, coupon200, points1500, shipping10) print(result) # 输出示例{商品总价: 6197.0, 优惠券抵扣: 200.0, 积分抵扣: 15.0, 运费: 10.0, 实付金额: 5992.0}2.4.4 列表推导式与生成器表达式对比列表推导式[要插入的值 for i in 数据集 if 条件]特点立即求值一次性生成整个列表并存入内存占用内存空间大。场景数据量不大需要全部立即生成的场景需要重复使用、多次访问的场景。生成器表达式(要插入的值 for i in 数据集 if 条件)特点惰性求值按需逐个生成元素无需同时存储所有元素节省内存。场景处理大数据集避免一次性加载所有数据到内存常用于sum()、max()、min()等函数的参数。完整对比示例import sys # 列表推导式 - 立刻生成全部数据占用内存 squares_list [x**2 for x in range(1000000)] print(f列表推导式占用内存{sys.getsizeof(squares_list)} 字节) # 约 8MB # 生成器表达式 - 惰性求值仅存储生成器对象本身 squares_gen (x**2 for x in range(1000000)) print(f生成器表达式占用内存{sys.getsizeof(squares_gen)} 字节) # 非常小 # 使用生成器作为 sum 的参数边生成边累加内存友好 total sum(x**2 for x in range(1000000)) # 无需额外存储列表 print(f总和{total}) # 当需要多次遍历时列表更合适生成器只能迭代一次 # 列表可以重复使用 my_list [x*2 for x in range(10)] print(sum(my_list)) # 可以多次使用 print(max(my_list))三、类型注解3.1 基本介绍类型注解是 Python 中的一种语法特性用于明确标识变量、函数参数和返回值的数据类型从而使代码更清晰、更安全、更易维护。类型推断是指 Python 解释器自动推断出变量、表达式或函数返回值的数据类型的能力而无需开发者显式声明。类型注解的写法变量名: 数据类型 值例如a: int 10 name: str Alice data: list[int] [1, 2, 3] mixed: str | int hello # Python 3.10 支持联合类型为什么要使用类型注解代码结构更清晰、逻辑更安全、易维护。更准确的代码自动提示IDE 支持。提前发现代码潜在问题借助静态检查工具如 mypy。注意Python 是动态类型语言添加的类型注解只是提示并不是强制约束3.2 函数类型注解为函数添加类型注解主要针对参数和返回值语法def 函数名(参数名: 类型, ...) - 返回值类型: ...示例def calculate_total( items: list[tuple[str, float, int]], # 商品列表[(名称, 单价, 数量)] coupon: float 0.0, # 优惠券金额 points: int 0 # 积分 ) - float: # 返回总金额 total sum(price * qty for _, price, qty in items) # 应用优惠逻辑... return total综合案例电商订单计算器含类型注解定义一个函数根据传入的商品信息、优惠和运费计算购物车总金额规则同上满 5000 可用优惠券和积分抵扣。为函数添加合理的类型注解可以极大提升代码的可读性和团队协作效率。from typing import List, Tuple, Dict def calculate_order_typed( items: List[Tuple[str, float, int]], # [(名称, 单价, 数量)] coupon: float 0.0, points: int 0, shipping: float 0.0 ) - Dict[str, float]: 带类型注解的订单计算器 total_goods sum(price * qty for _, price, qty in items) discount 0.0 if total_goods 5000 and coupon 0: discount min(coupon, total_goods) points_discount 0.0 if total_goods 5000 and points 100: usable_points (points // 100) * 100 points_discount usable_points / 100 max_discount total_goods - discount if points_discount max_discount: points_discount max_discount final_total total_goods - discount - points_discount shipping return { 商品总价: round(total_goods, 2), 优惠券抵扣: round(discount, 2), 积分抵扣: round(points_discount, 2), 运费: round(shipping, 2), 实付金额: round(final_total, 2) }对于需要团队协作开发和长期维护的项目推荐使用类型注解。四、结语函数是 Python 编程的核心构建块。从基础的参数传递到进阶的作用域、匿名函数再到现代化的类型注解掌握这些知识将帮助你写出更优雅、更健壮、更易维护的代码。希望本文的梳理能为你提供一份实用的参考手册。动手实践每个案例你会发现函数编程的魅力和力量。Happy Coding