一 模块与包的概念
在Python中,模块(Module)和包(Package)是组织和管理代码的基本方式,有助于提高代码的可维护性和可重用性。
1.1 模块:
- 定义: 模块是一个包含 Python 代码的文件(通常以 .py 为扩展名)。这个文件可以包含变量、函数、类等Python对象。
- 作用: 模块的主要作用是封装和组织代码,使得代码可以更好地结构化,同时支持代码的重用。可以在其他程序中导入模块并使用其中定义的功能。
- 示例: 假设有一个名为 example_module.py 的模块文件,其中包含如下内容:
# example_module.py def greet(name): return f"Hello, {name}!" def add_numbers(a, b): return a + b
在另一个Python文件中,可以通过导入该模块来使用其中的函数:
# main.py import example_module print(example_module.greet("Alice")) result = example_module.add_numbers(3, 5) print(result)
运行结果:
Hello,Alice
8
1.2 包(Package):
- 定义: 包是一个包含模块的文件夹,该文件夹中通常包含一个特殊的 init.py 文件,以标识该文件夹为一个包。
- 作用: 包的主要作用是将相关的模块组织在一起,形成一个命名空间。这样可以更好地管理大型项目中的代码,防止命名冲突,并提供更好的代码组织结构。
- 示例: 假设有一个名为 my_package 的包,其结构如下:
my_package/ ├── __init__.py ├── module1.py └── module2.py
init.py 文件可以为空,也可以包含初始化代码。module1.py 和 module2.py 是包含Python代码的模块文件。在其他文件中,可以通过导入包和模块的方式来使用:
# main.py from my_package import module1, module2 print(module1.function1()) result = module2.function2(10, 20) print(result)
通过模块和包的使用,Python程序可以更好地组织和管理代码,实现模块化和可重用的设计。
二 创建模块
首先,我们在一个包(文件夹)里创建三个模块。
其中两个模块分别是 hello 和 hello_from_the_other_side
我们将在call_hello 中尝试导入这两个模块
值得一提的是,在jupter notebook中导入模块得先把模块以.py的文件格式放在对应文件路径下。
不然会显示导入失败。
- hello模块内容如下:
def say_hello(): print("hello fishc.") def say_hi(): print("Hi Fishc.") def int(x): print(f"哈哈{x}")
里面定义了三个函数
- hello_from_the_other_side 模块内容如下:
def say_hello(): print("你好啊~") def say_hi(): print("嗨呀~")
里面定义了两个函数,其中两个函数与hello模块中的两个函数的函数名一致,但是内容不一样。
接下来我们将在call_hello这个脚本中尝试导入这两个模块。
共有四种导入模块的方式。
三 import 模块名
import hello hello.say_hi() hello.say_hello()
结果如下:
Hi Fishc.
hello fishc.
以这种方式导入模块时,在使用hello模块里的方法时,需要以模块名为前缀
四 from 模块名 import 方法名
使用这种方法导入hello模块的时候,再调用hello模块里的方法就不用再加模块名前缀了,代码如下:
from hello import say_hi,say_hello say_hi() say_hello()
结果如下:
Hi Fishc.
hello fishc.
虽然调用hello模块里的方法不用再加模块名前缀,但是在导入hello模块时,如果要调用模块的全部方法,还是很麻烦。
接下来介绍的方法 **from 模块名 import ***
就可以解决这个问题
五 from 模块名 import *
from hello import * say_hi() say_hello()
结果如下:
Hi Fishc.
hello fishc.
可以使用*代替所有函数,这种调用方式的优势是不用再一个个地去调用模块里的方法,但是容易造成命名冲突。
如下面这两个例子:
int("250")
结果如下:
哈哈250
这里的结果本意是将250这个字符串变成整数,但是执行结果却是打印了"哈哈250",这是因为call_hello脚本里本身也具有int()这个函数,所以发生了冲突,脚本执行int()时,选择执行模块里的int()方法
脚本中导入多个模块时,这多个模块具有相同的方法时,也会发生冲突,如下:
from hello import * from hello_from_the_other_side import * say_hi() say_hello()
结果如下:
嗨呀~
你好啊~
可以看到,如果两个方法的函数名相同,较迟导入模块的方法将覆盖较早导入模块的方法。
为了解决这种问题,我们可以使用import 模块名 as 自定义名字 的方法
六 import 模块名 as 自定义名字
import hello_from_the_other_side as h from hello import * h.say_hi() h.say_hello()
结果如下:
嗨呀~
你好啊~
可以看到,hello模块比hello_from_the_other_side更晚导入,但是我们使用import 模块名 as 自定义名字 的方法就可以很好地避免多个模块导入命名冲突的问题。