在 Python 中,__init__.py
文件是包(Package)的核心标识文件,它的存在使一个目录被 Python 解释器识别为「包」。这个文件有以下核心作用:
核心作用
-
标识包的存在
任何包含__init__.py
的目录都会被 Python 视为一个包,即使该文件为空。 -
包初始化代码
当包被首次导入时,__init__.py
中的代码会自动执行,可用于初始化配置(如环境变量、数据库连接、日志设置等)。 -
简化导入路径
可以在__init__.py
中预先导入子模块或子包,让外部调用者以更简洁的语法使用包的功能。
示例说明
1. 项目结构
假设有一个包 mypackage
,目录结构如下:
mypackage/
├── __init__.py # 包初始化文件
├── module1.py # 子模块1
└── module2.py # 子模块2
2. __init__.py
的典型用法
# mypackage/__init__.py
# 初始化代码(包被导入时自动执行)
print("Initializing mypackage...")
# 预先导入子模块,简化外部调用
from .module1 import MyClass
from .module2 import my_function
# 定义包级变量
VERSION = "1.0"
# 控制 `from mypackage import *` 的行为
__all__ = ['MyClass', 'my_function', 'VERSION']
3. 子模块代码
# mypackage/module1.py
class MyClass:
def __init__(self):
print("MyClass instance created!")
# mypackage/module2.py
def my_function():
print("my_function is called!")
4. 外部调用示例
# 外部脚本(main.py)
# 导入包时会自动执行 __init__.py 中的代码
import mypackage # 输出: "Initializing mypackage..."
# 直接使用 __init__.py 中预先导入的内容
obj = mypackage.MyClass() # 输出: "MyClass instance created!"
mypackage.my_function() # 输出: "my_function is called!"
# 访问包级变量
print(mypackage.VERSION) # 输出: "1.0"
关键特性
-
空文件也是合法的
即使__init__.py
为空,它依然标识目录为包。 -
控制导入行为
通过__all__
变量定义from mypackage import *
时暴露的内容。 -
命名空间包(Python 3.3+)
在 Python 3.3 及以上版本,即使没有__init__.py
,目录也可以作为命名空间包。但显式使用__init__.py
仍是推荐做法,以确保兼容性和明确性。
通过 __init__.py
,开发者可以灵活控制包的初始化逻辑和对外接口,使代码结构更清晰、使用更便捷。