Python编程
模块
模块是用来组织程序结构和创建可重用库的一种方式。一个模块通常存储在一个单独的 .py
文件中。许多模块是标准库的一部分,你也可以创建自己的模块。Python 会在当前目录和其他位置搜索模块;通过扩展 PYTHONPATH 环境变量以及其他方式,可以增加模块搜索的位置。
导入模块
import math
print(math.sqrt(10))
上面的代码导入了 math
标准模块,并且使该模块中的所有函数和类都可以通过模块名称来访问。
你可以为模块指定一个别名:
import math as Mathematics
print(Mathematics.sqrt(10))
你也可以只导入一个函数,使其不需要模块名前缀就能直接使用:
from math import sqrt
print(sqrt(10))
你还可以为导入的函数指定一个别名:
from math import cos as cosine
print(cosine(10))
你可以一次性导入多个模块:
import os, sys, re
也可以在函数内部延迟导入模块:
def sqrtTen():
import math
print(math.sqrt(10))
这种导入只会在函数被调用时发生。
你可以使用星号 *
导入模块中的所有函数,而不需要模块名前缀:
from math import *
print(sqrt(10))
然而,如果你在函数内部使用这种方式,在 Python 2 中会收到警告,在 Python 3 中会出错:
def sqrtTen():
from math import *
print(sqrt(10))
你可以通过 try...except
语句捕捉模块未找到的情况:
try:
import custommodule
except ImportError:
pass
模块的不同类型
模块可以是以下几种类型:
- Python 文件
- 共享对象(在 Unix 和 Linux 中)以
.so
为后缀 - DLL(在 Windows 中)以
.pyd
为后缀 - 目录
模块加载的顺序由 sys.path
控制。当前目录始终包含在搜索路径中。
目录应包含一个名为 __init__.py
的文件,该文件应包含在加载该目录时执行的 Python 命令。
创建与 Python 交互的 DLL 则另有专门的部分进行讲解。
检查模块是否导入
你可以检查一个模块是否已导入,方法如下:
if "re" in sys.modules:
print("Regular expression module is ready for use.")
创建模块
从文件创建模块
创建模块的最简单方法是拥有一个名为 mymod.py
的文件,该文件要么位于由 PYTHONPATH
变量识别的目录中,要么(更简单)就在当前工作目录中。如果你有以下文件 mymod.py
:
class Object1:
def __init__(self):
self.name = 'object 1'
你可以导入这个模块并创建 Object1
类的实例:
import mymod
myobject = mymod.Object1()
from mymod import *
myobject = Object1()
从目录创建模块
对于较大的项目,将所有类存储在一个文件中并不可行。通常,将所有文件存储在目录中并通过一个命令加载所有文件更为简便。每个目录需要有一个 __init__.py
文件,该文件包含在加载该目录时执行的 Python 命令。
假设我们有另外两个对象 Object2
和 Object3
,我们希望通过一个命令加载所有三个对象。然后我们创建一个名为 mymod
的目录,并在其中存储三个文件:Object1.py
、Object2.py
和 Object3.py
。这些文件可以包含每个文件的一个对象,但这不是必须的(尽管这样做更清晰)。然后我们会写一个 __init__.py
文件:
from Object1 import *
from Object2 import *
from Object3 import *
__all__ = ["Object1", "Object2", "Object3"]
前面三条命令告诉 Python 在有人加载模块时该做什么。最后的 __all__
定义告诉 Python 当执行 from mymod import *
时该做什么。通常,我们希望在模块的不同部分之间使用一些模块中的部分,例如我们希望在 Object2
中使用 Object1
。我们可以通过 from . import
*
命令轻松做到这一点,如下所示:
from . import *
class Object2:
def __init__(self):
self.name = 'object 2'
self.otherObject = Object1()
现在我们可以像上一节中那样导入 mymod
模块。
使程序可用作模块
为了使程序既能作为独立的命令行程序运行,又能作为模块使用,建议将所有代码放入函数和方法中,指定一个主函数,并在 __name__
内置变量等于 '__main__'
时调用该主函数。这样做的目的是确保当程序作为模块导入时,主函数中的代码不会被调用;如果代码直接放在函数外面,导入时代码会被调用。
你的程序(存储在 mymodule.py
中)可以如下所示:
def reusable_function(x, y):
return x + y
def main():
pass
# 任何你喜欢的代码
if __name__ == '__main__':
main()
使用上述程序的方式如下:
from mymodule import reusable_function
my_result = reusable_function(4, 5)
扩展模块路径
当请求导入时,模块会在由 sys.path
访问的目录(和 zip 文件?)中进行搜索。可以通过以下方式扩展模块路径:
import sys
sys.path.append("/My/Path/To/Module/Directory")
from ModuleFileName import my_function
在上面,如果 ModuleFileName.py
位于 /My/Path/To/Module/Directory
,并且包含 my_function
的定义,那么第二行确保第三行正常工作。
模块名称
模块名称似乎仅限于字母数字字符和下划线,不能使用破折号。虽然可以创建并运行 my-module.py
,但导入时 my-module
会失败。模块的名称是模块文件的名称去掉 .py
后缀。
模块名称区分大小写。如果模块文件叫做 MyModule.py
,那么 import mymodule
会失败,而 import MyModule
是有效的。
PEP 0008 推荐模块名使用全小写字母,可能会使用下划线。
内置模块
内置模块不同于标准库的一部分。例如,re
不是内置模块,而是一个用 Python 编写的模块;与此相对,_sre
是一个内置模块。
获取内置模块名称列表:
print(sys.builtin_module_names)
print("_sre" in sys.builtin_module_names) # True
print("math" in sys.builtin_module_names) # True