关于Python中的import(二)

上节简单说了 import 系统 和 __import__ 函数, 这节大概说下 importlib 中的 import_module, 和 package 相关的东西。

importlib.import_module(name, package=None)
name 是需要导入模块的名称,可以以相对或绝对方式导入;绝对方式是写上模块的绝对包路径,例如要导入 pkg 下的 module 模块,可以这样直接导入

import importlib

m = importlib.import_module('pkg.module')

返回值是模块对象 module,而不是 pkg ,这是和 __import__ 之间最大的区别,这也应该是 Python 官方文档上写的为什么不建议使用 __import__的主要原因,假如前面的包路径很长的话,如果用 __import__ 函数去导入的话只会返回最上层的那个 package 对象,那样用起来就很不方便。

至于 importlib.import_module 的相对路径方式,就必须要指定 package 参数,作为寻找名字为 name 的模块的锚点,大概是这种形式:

import importlib

#导入 pkg.mod
m = importlib.import_module('..mod', 'pkg.subpkg')

感觉这种方式应该很少用到。做个了解。

下面开始介绍 package

package 在 python 中好比文件系统中的文件和文件夹、package 负责管理模块和组织层级结构,package 也属于模块,但不是所有的模块都是 package, 可以理解为 .py 文件就是一个非 package 模块,而里面包含有一个 __init__.py 文件的文件夹即是一个 package module。 在 python 3.3 版本开始引入了新的概念,就是如果下面没有 __init__.py 文件, 这个文件夹同样是一个 package, 为了区分两者,前者称为 Regular packages, 后者称为 Namespace packages。

package 模块对象有一个 __path__ 属性,而普通的模块对象没有这个属性,这个属性是一个 存放 string 的可迭代对象,对象的值是一些路径,在导入它下面的子模块时,在这些路径下搜索子模块。

Regular packages

Regular package 的例子引用官方文档上的代码:

parent/
    __init__.py
    one/
        __init__.py
    two/
        __init__.py
    three/
        __init__.py

当导入 parent.one 时,parent/__init__.py 和 parent/one/__init__.py 会隐式执行,并且里面定义的变量会绑定到当前 package 的命名空间中。__init__.py 中可以像普通模块一样包含任何代码。

当通过 foo.bar.baz 形式导入模块时,最后一个冒号之前的名称必然都是package, 最后一个名称可能是 package 可能是 普通模块,说明普通模块不能包含子模块,import 系统首先会导入 foo, 然后再通过 foo.__path__ 找到 bar, 再通过 bar.__path__ 导入 baz, 中间环节如果导入失败,就会抛出一个 ModuleNotFoundError 异常。

这节先说到这,下节会说明导入模块的去向以及简单了解下 NameSpace package。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值