实际工程的组织架构一般是这样的:
bin包下的bin.py是实际的执行文件,my_mould包下的是业务逻辑的实现模板
bin.py需要import my_mould下的py文件,而bin和my_mould是平级的
所以在bin.py中直接import会报错:
from my_mould import main if __name__=='__main__': main.run()
结果:
Traceback (most recent call last):
File "E:/PyCode/模块/bin/bin.py", line 17, in <module>
from my_mould import main
ImportError: No module named 'my_mould'
找不到my_mould这个包,因为sys.path中的第一个当前路径是bin,而不是上一级“模板”,当前路径是“模板”才能import my_mould
如何解决这个问题:
版本一:把“模板”那一层加到sys.path
import sys sys.path.append(r'E:PyCode模块') from my_mould import main if __name__=='__main__': main.run()
结果:5
没问题,但是这样写死sys.path,代码移植到别人的电脑上就跑不起来了
版本二
利用os模板,从后面往前推,
找到当前文件:bin.py
再找到文件的绝对路径:E:PyCode模块inin.py
再找到上一级路径:E:/PyCode/模块/bin
最后找到上上级路径:E:/PyCode/模块
然后把这个路径定义为BASE_DIR,添加到sys.path
这里要用到方法:
print(__file__) #__file__表示文件本身,结果应该是bin.py,这里之所以是bin.py的绝对路径,是因为pycharm擅自加的,如果在cmd执行就是文件本身 print(os.path.abspath(__file__)) #abspath(__file__)才是python解释器给的正真的文件绝对路径 print(os.path.dirname(__file__)) #dirname(__file__)返回文件或文件夹的所处于的路径,也就是上一层路径 print(os.path.dirname(os.path.dirname(__file__))) #两层dirname(__file__),就是上上层
结果:
E:/PyCode/模块/bin/bin.py #python解释器给出的结果应该是bin.py
E:PyCode模块inin.py
E:/PyCode/模块/bin
E:/PyCode/模块
最终版本
import sys,os # BASE_DIR = os.path.dirname(os.path.dirname(__file__)) BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) #拿到 E:/PyCode/模板 这个路径 sys.path.append(BASE_DIR) # sys.path.append(r'E:PyCode模块') from my_mould import main if __name__=='__main__': # print(__file__) # print(os.path.abspath(__file__)) # print(os.path.dirname(__file__)) # print(os.path.dirname(os.path.dirname(__file__))) # BASE_DIR = os.path.dirname(os.path.dirname(__file__)) main.run()
所以,在日常开发中,结合os.path.abspath(__file__)使用os.path.dirname(__file__)是引用模板的常见方式。