Python 导入自建包报错ModuleNotFoundError: No module named xxx

Python015

Python 导入自建包报错ModuleNotFoundError: No module named xxx,第1张

如图,三个模块的关系:模块A导入模块B,而模块B导入模块C

执行模块A时,会报错ModuleNotFoundError: No module named xxx,说找不到模块C。

于是就打开模块B查看,发现导入模块C是正常的,这就让人很头疼

模块B和模块C是同一个包,而模块A又是在另一个包。同个包内的模块B可以用相对路径找到模块C,不同包的模块A则不能。

方案一:项目根目录为起始路径导入包

在IDE中执行python程序,编译器会自动把当前项目的根目录加入到包查找路径中,可以理解为加到PYTHONPATH下,所以导入写法如下:

方案二:导包时,把目标模块的路径加入包查找路径中

推荐使用方案一,养成好习惯,从项目根目录开始导包。

除了让包内导入更加显式,这个功能的一部分设计初衷是,为了帮助脚本解决同名文件出现在模块搜索路径上多个不同位置时的二义性。考虑包目录,这定义了一个名为mypkg 的包,其中含有名为mypkg.main和mypkg.string 的模块。现在,假设模块main试图导入名为string的模块。在 Python 2.X和更早版本中,Python会先寻找mypkg目录以执行相对导入。这会找到并导入位于该处的string.py文件,将其赋值给mypkg.main模块命名空间内的名称string。不过,这一导入的本意可能是要导入Python标准库的string模块。可惜的是,在这些Python版本中,无法直接忽略mypkg.string 去寻找位于模块搜索路径更右侧的标准库中的string模块。此外,我们无法使用完整包导入路径来解决这个问题,因为我们无法依赖在每台机器上的标准链接库路径。换句话说,包中的简单导入可能具有二义性而且容易出错。在包内,我们无法确定imports pam语句指的是包内的模块还是包外的模块。一种可能的后果是,一个局部的模块或包会在不经意间隐藏了sys.path 上的另一个模块。在实践中,Python使用者可以避免为他们自己的模块重复使用标准库模块的名称(如果需要标准string库,就不要把新的模块命名为string)。但是,一个包还是有可能意外地隐藏标准库模块。再者,Python 以后可能新增标准库模块,而其名称可能刚好就和自己的一个模块同名。而依赖于没有点号开头相对导入的程序代码同样也不容易理解,因为读者可能对希望使用哪个模块而感到困惑。所以我们最好能在代码中显式地指出导入的解析过程。

1、没有package的文件夹设置为source,设置包的方式有两种:

第一种:首先选中自定义包,右键按照图示选择Sources Root即可

第二种:在settings设置界面,如图所示将自定义包设置sources