Python3 模块基础

模块

什么是模块

模块就是一系列功能的集合体, 而函数是某一功能的集合体, 因此模块可以看成是一堆函数的集合体

模块的四种形式

  • 自定义模块
  • 第三方模块 (通过pip安装)
  • 内置模块

导入模块

import 模块

impoort time
  1. 开辟内存空间, 内存空间命名为time
  2. 把time.py中的所有代码读入名称空间, 然后运行
  3. 通过time.方法使用time模块中的方法
  • 优点: 通过time.方法使用方法, 因此不存在变量名和方法名冲突

  • 缺点: 每次使用方法都要加上time.前缀

from 模块 import 方法

from time import sleep
  1. 开开辟内存空间, 内存空间命名为time
  2. 把time.py中所有代码读入名称空间, 然后运行
  3. 把sleep()读入当前运行文件, 因此可以通过方法名直接使用该方法

一次导入多个方法:

from time import time, sleep

一次导入全部方法:

from time import *
  • 优点: 使用方法时不用加上time.前缀
  • 缺点: 方法名可能会和变量名有冲突

循环导入

现在有两个.py文件

# m1.py
from m2 import y
x = 10
print('m1:', x+y)
# m2.py
from m1 import x
y = 20
print('m2:', x+y)

我们现在执行m1.py文件, 结果: ImportError: cannot import name 'y'

  1. m1.py 执行from m2 import y代码, 创建m2模块空间并会执行m2.py代码
  2. m2.py执行from m1 import x代码, 创建m1模块空间并执行m1.py代码
  3. 由于模块名称空间只会开辟一次, 因此执行m1.py代码时会跳过from m2 import y代码
  4. x = 10
  5. print('m1:', x+y) 报错

我们可以通过定义函数来解决这个问题, 因为定义函数只检测语法不执行代码

# m1.py
def func():
    from m2 import y

x = 10    
func()    

print('m1:', x+y)
# m2.py
def func():
    from m1 import x

y = 20
print('m2:',x+y)

模块搜索路径

模块的搜索路径顺序

  1. 内存中已经导入的模块

  2. 内置模块

  3. 自定义模块(环境变量)

Python文件的两种用途

  1. 执行文件 : 用来被执行使用

  2. 模块文件 : 用来被导入使用

现在我们定义一个module.py模块文件

def func():
	print('from func')

 func()

我们再定义一个script.py执行文件

from module import func

我们现在运行script.py文件, 只是想导入func方法, 结果: from func

解决上述问题, 我们可以将module.py改造为:

def func():
	print('from func')

if __name__ == '__main__':
    func()

当module.py文件为模块文件时候, __name__ = 文件名, 当module.py为执行文件时, __name__ == '__main__'

什么是包

包是模块的一种形式, 就是含有一个__init__.py文件的文件夹, 导入包就是导入__init__.py

为什么要有包

当模块内部函数过多, 为了方便管理模块, 把一个模块划分为多个模块, 但是又不能改变导入方式, 把模块放入一个包(文件夹)内

包的使用

现有如下模块文件a.py:

# a.py

def f1():
    pass

def f2():
    pass



def f3():
    pass

def f4():
    pass

导入 a 模块后, 我们可以用下面的方法使用a内的方法

import a
a.f1()
a.f2()
a.f3()
a.f4()

现在我们将 a 模块改为包的形式

  1. 我们新建一个包文件夹, 将包文件夹命名为 a , 然后在文件夹内新建一个__init__.py文件
  2. 然后我们将原来a.py中的方法分为两类, 分别存放在m1.pym2.py文件中
# m1.py

def f1():
    pass

def f2():
    pass
# m2.py

def f3():
    pass

def f4():
    pass

现在我们可以通过 from a.m1 import f1来导入f1()方法, 但这改变了导入方式, 显然不符合包的思想, 于是:

# __init__.py

from a.m1 import f1
from a.m1 import f2

from a.m2 import f3
from a.m2 import f4

然后, 我们就可以import a , 然后通过 a.f1() 来使用f1()方法

注意: 模块文件 m1.py 和 m2.py 的搜索路径以执行文件为准

绝对导入和相对导入

绝对导入

from a.m1 import f1
from a.m1 import f2

相对导入

  1. . 代表当前被导入文件所在的文件夹
  2. .. 代表被导入文件所在的文件夹的上一级
  3. ... 代表当前被导入文件所在的文件夹的上一级的上一级
from .m1 import f1
from .m2 import f2
posted @ 2019-09-26 16:07  MrBigB  阅读(249)  评论(0编辑  收藏  举报