Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/335.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python:如何导入没有Python文件名作为子模块的模块? 描述_Python_Python 3.x_Module_Python Import - Fatal编程技术网

Python:如何导入没有Python文件名作为子模块的模块? 描述

Python:如何导入没有Python文件名作为子模块的模块? 描述,python,python-3.x,module,python-import,Python,Python 3.x,Module,Python Import,假设我有一个具有以下结构的包: package-folder |_ mypackage |_ __init__.py |_ module1.py setup.py 其中\uuuu init\uuuu.py为空且 module1.py: def do_stuff(): print('Did stuff.') setup.py包含使用此文件包制作软件包的常用上下文,可以在本地系统上使用pip install-e pkgpath安装该软件包 在script.py

假设我有一个具有以下结构的包:

package-folder
  |_ mypackage
     |_ __init__.py
     |_ module1.py
  setup.py
其中
\uuuu init\uuuu.py
为空且

module1.py

def do_stuff():
    print('Did stuff.')
setup.py
包含使用此文件包制作软件包的常用上下文,可以在本地系统上使用
pip install-e pkgpath
安装该软件包

script.py
中,我必须执行以下操作:

import mypackage as abbr

abbr.module1.do_stuff()
# output: Did stuff.
我想要的电话是:

abbr.do_stuff()
# output: Did stuff.
问题
  • 我如何“组织”我的包,以便直接从
    abbr.function()
    调用module1.py以外的函数?需要更改哪些代码
  • 如果包增长,此组织是否有用?所以目录将充当结构元素,python文件只是用来组织我的函数的胶囊
  • 在模块和子模块中组织功能的最佳方式是什么

  • 进一步思考
    • 是否有充分的理由不在每个python文件中只包含一个可以从模块中使用的函数?(并且与文件同名)
    • 我假设,我将不得不修改我的
      \uuuu init\uuuu.py
      -文件,但我不知道如何修改
    对问题2的澄清 电话应为:

    abbr.do_stuff1()
    abbr.subpackage.do_stuff2()
    
    而不是:

    abbr.module1.do_stuff1()
    abbr.subpackage.module2.do_stuff2()
    

    您已经非常接近答案了,只需要从
    \uuu init\uuuu.py
    导入方法

    您还可以添加特殊变量
    \uuuuu all\uuuu
    ,该变量是用户希望在该文件中找到的变量/函数/等的列表

    \uuuu init\uuuuuuuuuuuuupy
    @
    mypackage

    from .module1 import do_stuff1
    
    __all__ = ['do_stuff1']
    
    from .module2 import do_stuff2
    
    __all__ = ['do_stuff2']
    
    \uuuu init\uuuuuuuuuuuuupy
    @
    子包

    from .module1 import do_stuff1
    
    __all__ = ['do_stuff1']
    
    from .module2 import do_stuff2
    
    __all__ = ['do_stuff2']
    
    编辑: 要使顶级软件包导入所有子软件包符号,可以将
    \uuu init\uuuuuuuupy
    @
    mypackage
    更改为:

    import pkgutil
    
    from .module1 import do_stuff1
    
    __all__ = ['do_stuff']
    
    for loader, name, is_pkg in  pkgutil.walk_packages(__path__):
        module = loader.find_module(name).load_module(name)
        __all__.extend(module.__all__)
        for var in module.__all__:
            globals()[var] = getattr(module, var)
    

    然后,您不仅可以调用
    abbr.subpackage.do_stuf2()
    ,而且还可以调用
    abbr.do_stuf2()

    关于问题1,您的解决方案有效!伟大的但是如果有一个“大”的包裹,这不是有点乱吗?难道没有更好的办法吗?此外,还有一个代码被截取,它应该加载“所有”子模块,但我无法让它工作。除此之外,一些“指南”建议最好将init.py留空。最后一条评论:但是什么是“最好”的方法呢?我不会考虑离开<代码>第二个ITITY。Py < /C>空一个重新组合,这是一个你拥有的选项,但是它给了你一个非常有力的方式来提供简单的对象访问,同时保持代码有组织的方式。在一些
    \uuuu init\uuuuuuuuuupy
    中,我确实使用脚本而不是手动导入,但子包太扁平了,这就是,能够执行
    缩写为do_stuff2()
    。你能给出一个示例脚本吗?@Laenan我现在没有脚本的副本,但我基本上覆盖了所有子包(目录)将其所有变量中的所有内容导入主程序包。@Laenan我在答案中添加了一个未经检查的脚本,请检查这是否适用于您。基本上,它将获取子包的
    \uuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuuu
    变量中的。