包的相对导入__init __。py

时间:2017-03-05 23:10:02

标签: python packages python-module

假设我有一个包含两个子模块的包以及__init__.py本身的大量代码:

pkg/__init__.py
pkg/foo.py
pkg/bar.py

并且,为了使计划的未来重构更容易,我希望包的组件专门使用相对导入来相互引用。特别是,import pkg永远不会出现。

foo.py我可以做到

from __future__ import absolute_import
from . import bar

访问bar.py模块,反之亦然。

问题是,我以这种方式写入导入__init__.py的内容是什么?我想要与import pkg as local_name完全相同的效果,只需要不必指定绝对名称pkg

#import pkg as local_name
from . import ??? as local_name

更新:受到maxymoo的回答启发,我试过了

from . import __init__ as local_name

这不会将local_name设置为__init__.py定义的模块;它改为获得该模块的__init__ 方法的绑定方法包装器。我想我能做到

from . import __init__ as local_name
local_name = local_name.__self__

得到我想要的东西,但是(a)哎呀,(b)这让我担心模块还没有完全初始化。

答案需要处理 Python 2.7和Python 3.4 +。

是的,掏空__init__.py并让它从子模块中重新导出东西可能会更好,但这种情况还不会发生。

2 个答案:

答案 0 :(得分:1)

  • python2和python3(使用discouraged __import__):

      来自第一级模块的
    • pkg.foopgk.bar,...):

      local_name = __import__("", globals(), locals(), [], 1)
      
    • 来自子包中的模块(pkg.subpkg.foo,...):

      local_name = __import__("", globals(), locals(), [], 2)
      
  • 仅限python3 *:

    • 来自pkg.foopkg.bar

      import importlib
      local_name = importlib.import_module("..", __name__)
      
    • 来自pkg.subpkg.baz

      import importlib
      local_name = importlib.import_module("...", __name__)
      
不幸的是,在这种情况下,python2上的

* import_module尝试加载pkg.

答案 1 :(得分:0)

dunders没什么特别的(他们在编写你自己的模块/函数名时只是气馁);你应该能够做到

this.state.content