模块就像工具箱里的一个个工具,包就像装工具的工具箱
学完本章,你会:
✅ 理解模块和包的概念
✅ 掌握如何导入和使用模块
✅ 了解Python标准库
✅ 学会安装第三方包
✅ 能创建自己的模块和包
✅ 理解if __name__ == "__main__"的作用
📁 第一部分:模块 - 代码的"工具箱"
现实比喻:
模块 = 一个工具箱 🔧
函数 = 工具箱里的工具
变量 = 工具箱里的零件
类 = 工具箱里的复杂工具
技术定义:模块就是一个.py文件,包含Python定义和语句。
为什么需要模块?
没有模块的世界:
# 一个超大的文件,有10000行代码# 前面3000行是数学工具# 中间3000行是字符串处理工具# 后面4000行是文件处理工具# 想找一个函数?翻几千行代码# 想修改一个功能?可能影响其他地方# 和别人合作?文件冲突
有模块的世界:
# math_tools.py - 数学工具# string_tools.py - 字符串工具# file_tools.py - 文件工具# 需要哪个工具,导入哪个模块# 清晰、整洁、易维护
🔧 第二部分:使用模块
导入模块的三种方式
方式1:import 模块名
# 导入整个模块import math# 使用模块中的函数result = math.sqrt(16) # 4.0print(f"16的平方根: {result}")# 使用模块中的变量print(f"圆周率: {math.pi}") # 3.141592653589793# 使用模块中的函数angle = 45radians = math.radians(angle) # 角度转弧度print(f"{angle}度 = {radians}弧度")
优点:
缺点:
方式2:from 模块名 import 功能
# 导入特定功能from math import sqrt, pi# 直接使用,不用写模块名result = sqrt(25) # 5.0print(f"25的平方根: {result}")print(f"圆周率: {pi}")# 导入多个功能from math import sin, cos, tanangle = 30rad = math.radians(angle)print(f"sin({angle}°) = {sin(rad):.2f}")# 导入所有功能(不推荐)# from math import * # 导入所有,可能造成命名冲突
优点:
缺点:
方式3:给模块起别名
# 给模块起简短的名字import numpy as npimport pandas as pdimport matplotlib.pyplot as plt# 使用# data = pd.read_csv("data.csv")# 这样代码更简洁
🎪 第三部分:Python标准库
Python自带了很多有用的模块,这些就是标准库。
常用标准库模块
示例:几个常用模块
# 1. random - 随机数import random# 随机整数dice = random.randint(1, 6) # 1-6的随机整数print(f"掷骰子: {dice}")# 随机选择colors = ["红", "绿", "蓝", "黄"]lucky_color = random.choice(colors)print(f"幸运颜色: {lucky_color}")# 打乱顺序cards = ["A", "K", "Q", "J", "10"]random.shuffle(cards)print(f"洗牌后: {cards}")
# 2. datetime - 日期时间from datetime import datetime, date, timedelta# 当前时间now = datetime.now()print(f"当前时间: {now}")print(f"年: {now.year}, 月: {now.month}, 日: {now.day}")# 格式化时间formatted = now.strftime("%Y年%m月%d日 %H:%M:%S")print(f"格式化: {formatted}")# 计算日期today = date.today()tomorrow = today + timedelta(days=1)print(f"今天: {today}, 明天: {tomorrow}")
# 3. os - 文件操作import os# 获取当前目录current_dir = os.getcwd()print(f"当前目录: {current_dir}")# 列出目录内容# files = os.listdir(".") # 列出当前目录# for file in files:# print(file)# 检查文件是否存在if os.path.exists("test.txt"): print("test.txt 存在")else: print("test.txt 不存在")
# 4. time - 时间控制import timeprint("开始计时...")time.sleep(1) # 暂停1秒print("1秒后...")time.sleep(0.5) # 暂停0.5秒print("又过了0.5秒...")# 计算程序运行时间start = time.time()# 模拟一些操作for i in range(1000000): passend = time.time()print(f"循环耗时: {end - start:.4f}秒")
🎁 第四部分:安装和使用第三方包
什么是第三方包?
Python标准库:Python自带的,不用安装
第三方包:别人写的,需要安装才能用
为什么需要第三方包?
扩展Python功能
避免重复造轮子
有很多优秀的专业包
使用pip安装包;pip是Python的包管理工具,就像手机的"应用商店"。
# 安装包pip install 包名# 安装特定版本pip install 包名==版本号# 升级包pip install --upgrade 包名# 卸载包pip uninstall 包名# 列出已安装的包pip list# 保存包列表到文件pip freeze > requirements.txt# 从文件安装包pip install -r requirements.txt
常用第三方包:
示例:使用requests包
# 先安装:pip install requestsimport requests# 发送GET请求response = requests.get("https://api.github.com")print(f"状态码: {response.status_code}") # 200表示成功print(f"内容类型: {response.headers['content-type']}")# 获取JSON数据if response.status_code == 200: data = response.json() # 如果是JSON,转换为字典 print(f"GitHub API版本: {data.get('current_user_url')}")# 发送POST请求(带参数)url = "https://httpbin.org/post"data = {"name": "张三", "age": 25}response = requests.post(url, data=data)print(f"POST响应: {response.json()}")# 下载文件url = "https://www.python.org/static/img/python-logo.png"response = requests.get(url)with open("python_logo.png", "wb") as f: f.write(response.content)print("文件下载完成")
🏗️ 第五部分:创建自己的模块
创建第一个模块
步骤1:创建模块文件
# 保存为 calculator.py# 这是一个计算器模块def add(a, b): """加法""" return a + bdef subtract(a, b): """减法""" return a - bdef multiply(a, b): """乘法""" return a * bdef divide(a, b): """除法""" if b == 0: return "错误:除数不能为0" return a / b# 模块级别的变量PI = 3.14159VERSION = "1.0.0"
步骤2:使用自己的模块
# 保存为 main.py,和calculator.py在同一个目录import calculator# 使用模块中的函数result1 = calculator.add(10, 5)result2 = calculator.multiply(3, 4)result3 = calculator.divide(10, 2)print(f"10 + 5 = {result1}")print(f"3 × 4 = {result2}")print(f"10 ÷ 2 = {result3}")# 使用模块中的变量print(f"π的值: {calculator.PI}")print(f"版本: {calculator.VERSION}")# 也可以这样导入from calculator import add, subtractprint(f"使用直接导入: 8 - 3 = {subtract(8, 3)}")
添加文档字符串
"""calculator.py这是一个计算器模块,提供基本的数学运算功能。作者: 张三版本: 1.0.0"""def add(a, b): """ 计算两个数的和 参数: a -- 第一个数 b -- 第二个数 返回: 两个数的和 """ return a + b# 其他函数...
查看模块信息:
import calculator# 查看模块文档print(calculator.__doc__)# 查看函数文档print(calculator.add.__doc__)# 查看模块有哪些功能print(dir(calculator))
📦 第六部分:创建包
什么是包?
包就是包含多个模块的文件夹。
目录结构:
my_package/ # 包目录├── __init__.py # 包的初始化文件├── module1.py # 模块1├── module2.py # 模块2└── subpackage/ # 子包 ├── __init__.py └── module3.py
创建简单的包
步骤1:创建包结构
my_math/ # 包名├── __init__.py # 必须有的文件├── basic.py # 基本运算模块├── advanced.py # 高级运算模块└── utils.py # 工具模块
步骤2:编写模块
# my_math/basic.py"""基本数学运算"""def add(a, b): return a + bdef multiply(a, b): return a * b# my_math/advanced.py"""高级数学运算"""def power(base, exp): return base ** expdef factorial(n): if n == 0: return 1 return n * factorial(n - 1)# my_math/utils.py"""工具函数"""def is_even(n): return n % 2 == 0def is_prime(n): if n < 2: return False for i in range(2, int(n ** 0.5) + 1): if n % i == 0: return False return True
步骤3:编写init.py
"""my_math 包一个数学工具包"""# 导入包中的模块from .basic import add, multiplyfrom .advanced import power, factorialfrom .utils import is_even, is_prime# 包版本__version__ = "1.0.0"__author__ = "张三"# 可以在这里定义包级别的变量PI = 3.141592653589793E = 2.718281828459045
步骤4:使用包
# 方法1:导入整个包import my_mathprint(f"5 + 3 = {my_math.add(5, 3)}")print(f"5的阶乘 = {my_math.factorial(5)}")print(f"7是质数吗? {my_math.is_prime(7)}")print(f"π = {my_math.PI}")# 方法2:从包中导入特定模块from my_math import basic, advancedprint(f"使用basic模块: 4 × 6 = {basic.multiply(4, 6)}")print(f"使用advanced模块: 2³ = {advanced.power(2, 3)}")# 方法3:从包中导入特定功能from my_math.basic import addfrom my_math.utils import is_evenprint(f"直接导入: 10 + 20 = {add(10, 20)}")print(f"10是偶数吗? {is_even(10)}")
🎯 第七部分:if __name__ == "__main__"
理解这个魔法语句
问题:当一个模块被导入时,里面的代码都会被执行。
# calculator.pydef add(a, b): return a + bdef test(): print("测试add函数...") print(f"2 + 3 = {add(2, 3)}")# 这行代码在导入时也会执行test() # 问题:别人导入这个模块时,测试代码也会运行
解决方案:使用if __name__ == "__main__"
# calculator.pydef add(a, b): return a + bdef test(): print("测试add函数...") print(f"2 + 3 = {add(2, 3)}")# 只有直接运行这个文件时,才会执行if __name__ == "__main__": test() print("calculator.py 被直接运行")else: print(f"calculator.py 被导入为模块,模块名: {__name__}")
__name__变量的值
文件被直接运行:__name__ == "__main__"
文件被导入:__name__ == 模块名
示例:
# 文件: my_module.pyprint(f"__name__ 的值是: {__name__}")if __name__ == "__main__": print("这个文件被直接运行")else: print("这个文件被导入")# 文件: main.pyimport my_moduleprint("main.py 执行完成")
运行结果:
# 直接运行 my_module.py__name__ 的值是: __main__这个文件被直接运行# 运行 main.py__name__ 的值是: my_module这个文件被导入main.py 执行完成
实际应用:
# 一个完整的模块示例def add(a, b): """加法""" return a + bdef subtract(a, b): """减法""" return a - bdef multiply(a, b): """乘法""" return a * bdef divide(a, b): """除法""" if b == 0: return "错误:除数不能为0" return a / bdef run_tests(): """运行测试""" print("运行测试...") print(f"测试 add: 5 + 3 = {add(5, 3)}") print(f"测试 subtract: 10 - 4 = {subtract(10, 4)}") print(f"测试 multiply: 6 * 7 = {multiply(6, 7)}") print(f"测试 divide: 15 / 3 = {divide(15, 3)}") print(f"测试 divide 除零: 5 / 0 = {divide(5, 0)}") print("测试完成!")def main(): """主函数""" print("=== 计算器程序 ===") print("1. 加法") print("2. 减法") print("3. 乘法") print("4. 除法") choice = input("请选择操作 (1-4): ") a = float(input("输入第一个数: ")) b = float(input("输入第二个数: ")) if choice == "1": result = add(a, b) print(f"结果: {a} + {b} = {result}") elif choice == "2": result = subtract(a, b) print(f"结果: {a} - {b} = {result}") elif choice == "3": result = multiply(a, b) print(f"结果: {a} × {b} = {result}") elif choice == "4": result = divide(a, b) print(f"结果: {a} ÷ {b} = {result}") else: print("无效的选择")# 如果是直接运行这个文件,执行主程序# 如果是被导入,不执行主程序if __name__ == "__main__": main()
🎮 练习时间
练习1:创建自己的模块
# 任务:创建一个string_utils.py模块# 包含以下函数:# 1. reverse_string(s) - 反转字符串# 2. count_vowels(s) - 统计元音字母数量# 3. is_palindrome(s) - 判断是否是回文# 4. 添加测试代码,用if __name__ == "__main__"保护# 完成后,创建另一个文件main.py,导入并使用这个模块
练习2:安装和使用第三方包
# 任务:安装colorama包,让终端输出有颜色# 1. pip install colorama# 2. 使用colorama输出彩色文本# 3. 创建一个彩色日志系统from colorama import init, Fore, Back, Styleinit(autoreset=True) # 自动重置颜色print(Fore.RED + "这是红色文字")print(Back.GREEN + "这是绿色背景")print(Style.BRIGHT + "这是加粗文字")
练习3:理解模块导入
# 文件结构:# project/# ├── utils/# │ ├── __init__.py# │ ├── math_utils.py# │ └── string_utils.py# └── main.py# 任务:在math_utils.py中定义一些数学函数# 在string_utils.py中定义一些字符串函数# 在main.py中导入并使用它们# 理解相对导入和绝对导入
💡 常见错误
错误1:模块找不到
# ❌ 错误import mymodule # ModuleNotFoundError: No module named 'mymodule'# ✅ 解决方法:# 1. 确保模块文件在当前目录# 2. 确保模块文件是.py文件# 3. 检查文件名拼写
错误2:循环导入
# ❌ 错误:a.py 导入 b.py,b.py 又导入 a.py# a.pyimport b# b.pyimport a # 循环导入,可能导致错误# ✅ 解决方法:# 重新设计代码结构,避免循环导入
错误3:包缺少init.py
# ❌ 错误my_package/ module1.py module2.py# 缺少__init__.py,Python不认为这是包# ✅ 解决方法:# 添加空的__init__.py文件
错误4:导入顺序问题
# ❌ 不推荐的导入顺序import sysimport osfrom mymodule import somethingimport math # 标准库应该在最前面# ✅ 推荐的导入顺序:# 1. 标准库# 2. 第三方库# 3. 自己的模块import mathimport osimport sysimport requestsimport pandasfrom mymodule import something
📊 模块和包总结
📋 检查清单
🎉 恭喜!模块和包掌握完成现在你已经学会了如何组织Python代码:
关键收获:
✅ 模块:把代码分到不同文件
✅ 包:把模块分到不同文件夹
✅ 导入:使用别人的代码
✅ 标准库:Python自带的工具
✅ 第三方包:扩展Python功能
✅ 创建模块:分享自己的代码
现在你可以:
把大项目拆分成小模块
使用丰富的Python生态系统
安装和使用专业工具
创建可重用的代码库
更好地组织测试代码
下一章预告:文件操作 - 读写数据
你会学习如何读取和写入文件,处理各种格式的数据,这是自动化测试的重要技能!
准备好了吗?让我们继续前进!🚀
小提示:模块和包就像乐高积木,小的模块组合成大的系统。先学会用别人的"积木",再学会做自己的"积木",最后就能搭建复杂的"建筑"了!