[Python学习]__import__与reload要注意的

来源:互联网 发布:java 对象equals方法 编辑:程序博客网 时间:2024/06/05 06:02

__import__可以把字符串形式的模块进行导入,但有一点要注意,你需要让python知道如何找到这个模块,因此这个模块的路径可能需要加到 sys.path 中去。那么在我写的meteor模块处理模块中我遇到一个问题,当python格式的模板(它就是使用__import__来导入模板的)被导入后,然后进行了修改,如何重新导入使其生效呢。那么就可以使用reload来实现。代码如下:

        dirname = os.path.dirname(os.path.abspath(modulename))
        filename, ext = os.path.splitext(os.path.basename(modulename))
        if ext.lower() != ‘.py’:
            return {}, {}
        if dirname:
            sys.path.insert(0, dirname)
        if sys.modules.has_key(filename):
            mod = sys.modules[filename]
            reload(mod)
        else:
            mod = __import__(filename)
        if dirname:
            del sys.path[0]

这段代码是用来导入一个python的文件,你传给一个字符串格式的python文件名,如:template/tmpl.py。如果有目录则将其插入到sys.path中,最后再删除。如果在sys.modules已经存在此模块,说明以前导入过,则调用reload重新装入,否则是一个未导入过的模块,可以使用__import__进行导入。

问题就是原来代码不是这样写的,可能是这样:

        dirname = os.path.dirname(os.path.abspath(modulename))
        filename, ext = os.path.splitext(os.path.basename(modulename))
        if ext.lower() != ‘.py’:
            return {}, {}
        if sys.modules.has_key(filename):
            mod = sys.modules[filename]
            reload(mod)
        else:
            if dirname:
                sys.path.insert(0, dirname)
            mod = __import__(filename)
            if dirname:
                del sys.path[0]

注意背影为红色的代码,也就是说在调用reload()之前没有对路径的处理。这样做报了一个错,说是找不到模块。因此才改成开始的代码。

那么这个问题就是说,因为reload()与__import__差不多都需要在sys.path中可以找到模块,因此都需要把路径加进去。尽管你可以从sys.modules中得到模块对象,但reload()是需要从源码重新导入的,依然需要通过sys.path来导入模块。

不过,这段代码最后变成了:

        dirname = os.path.dirname(os.path.abspath(modulename))
        filename, ext = os.path.splitext(os.path.basename(modulename))
        if ext.lower() != ‘.py’:
            return {}, {}
        if sys.modules.has_key(filename):
            del sys.modules[filename]
        if dirname:
            sys.path.insert(0, dirname)
        mod = __import__(filename)
        if dirname:
            del sys.path[0]

没有使用reload()不过功能是一样的。


原创粉丝点击