5

我想在事先不知道其名称的情况下导入子模块,

>>> __import__("os.path")
<module 'os' from '/usr/lib/python3.3/os.py'>

不像你想象的那样工作,返回os,不是os.path

我想出了这个解决方案。

def import_submodule(mod, submod):
    ns = {}
    exec_str = "from %s import %s as submod" % (mod, submod)
    exec(exec_str, ns, ns)
    return ns["submod"]

这给出了结果:

>>> import_submodule("os", "path")
<module 'posixpath' from '/usr/lib/python3.3/posixpath.py'>

但是,我宁愿不使用 exec() ,因为它的做法很糟糕,并且当 Python 的导入机制已经通过__import__,impimportlib模块可用时似乎没有必要。

Python3.x 中有没有办法通过函数调用而不是使用来进行这种导入exec()

4

2 回答 2

5

使用importlib.import_module

>>> import importlib
>>> importlib.import_module('os.path')
<module 'posixpath' from '/usr/lib/python2.7/posixpath.pyc'>

这应该适用于 python2.7+ 和 3.1+。

于 2013-09-27T14:48:20.823 回答
3

请注意,如果您想 do:from A import B as C作为函数调用,importlib.import_module则并不总是有效,因为B可能不是模块。

Heres a function which uses importlib and getattr.

def my_import_from(mod_name, var_name):
    import importlib
    mod = importlib.import_module(mod_name)
    var = getattr(mod, var_name)
    return var

So this:

from os.path import dirname as var

Can be replaced with this:

var = my_import_from("os.path", "dirname")

Which avoids exec and allows both submodules and any variables defined in the module.

Since my question explicitly says importing a submodule, the answer from @Bakuriu is correct, however including this for completeness and it may help others who run into the same problem.

于 2013-09-28T09:46:37.213 回答