本文共 4936 字,大约阅读时间需要 16 分钟。
本文主要讲解,在终端(Linux终端或windows终端)场景下运行python3程序时候的,容易出现的 No module name "XXXX"情况。在Pycharm下的兼容性很好,一般不会出现类似问题。
# run.py文件import sysfrom Business import buyfrom Tools import make_moneyprint(buy.house)print(make_money.work)print(sys.path)
使用终端运行(Pycharm里面的Terminal或系统自带终端都行),结果如下:
别野Tester['D:\\MyProjects\\ModuleImport', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts\\python37.zip', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\Lib', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib\\site-packages', 'D:\\MyProjects\\EMQuantAPI_Python\\python3']
重点:环境变量的第一个变量,是此项目的根目录,也就是运行文件run.py所在的目录
# buy.py文件car = "牧马人"house = "别野"import sysprint(sys.path)
['D:\\MyProjects\\ModuleImport\\Business', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts\\python37.zip', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\Lib', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib\\site-packages', 'D:\\MyProjects\\EMQuantAPI_Python\\python3']
重点:环境变量的第一个变量,是运行文件buy.py所在的目录
以上两种情况,只是想表达:
1.无论你在哪里运行py文件,系统都会默认把py文件所在的目录加入到环境变量中。 2.因为有了环境变量有这个地址,所以才能直接在终端导入这个模块,否者报错:no Module name “XXXX” 3.无法导入某个模块,肯定是因为环境变量里面没有这个模块所在的地址(注意:这个模块所在的地址与这个模块里面文件的所在的地址不一样)
# run.py文件# 方式一:# import Business.buy# import Tools.make_money# # print(Business.buy.car)# print(Tools.make_money.work)# 方式二:推荐使用from Business import buyfrom Tools import make_moneyprint(buy.house)print(make_money.work)
# 最终的结果为:别野Tester
1.因为我们运行的文件run.py文件在根目录下,系统会默认把’D:\MyProjects\ModuleImport’这个地址加入到系统变量中。且Business模块和Tools模块也在这个根目录下面,所以直接在run.py文件里面导入,顺理成章!
# 修改后的buy.py文件car = "牧马人"house = "别野"from Tools import make_moneyprint(make_money.work)
# make_money.py文件work = "Tester"
在pycharm里面直接运行buy.py文件,没问题的。但在终端运行会报错的,具体如下:
分析:
1.我们运行的buy.py文件,默认把buy.py所在的目录添加到系统变量中,而Tools模块所在的目录,不会自动添加到环境变量中,所以无法导入Tools模块。
# 修改后的buy.py文件----证明Tools模块的目录没有添加到环境变量中car = "牧马人"house = "别野"import sysprint(sys.path)from Tools import make_moneyprint(make_money.work)
['D:\\MyProjects\\ModuleImport\\Business', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts\\python37.zip', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\Lib', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib\\site-packages', 'D:\\MyProjects\\EMQuantAPI_Python\\python3']Traceback (most recent call last): File "buy.py", line 6, infrom Tools import make_moneyModuleNotFoundError: No module named 'Tools'
# 修改后的buy.py文件import sys, ostools_path = os.path.join(os.getcwd(), "..")print("tools_path:", tools_path)sys.path.append(tools_path)print(sys.path)from Tools import make_moneyprint(make_money.work)
tools_path: D:\MyProjects\ModuleImport\Business\.. # 这个才是添加的模块目录,其实就是"D:\MyProjects\ModuleImport"['D:\\MyProjects\\ModuleImport\\Business', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts\\python37.zip', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\Scripts', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\Lib', 'C:\\Users\\admin\\AppData\\Local\\Programs\\Python\\Python37\\DLLs', 'C:\\Users\\admin\\Envs\\AutoTestEnv', 'C:\\Users\\admin\\Envs\\AutoTestEnv\\lib\\site-packages', 'D:\\MyProjects\\EMQuantAPI_Python\\python3', 'D:\\MyProjects\\ModuleImport\\Business\\..']Tester# 环境变量里面,也有了如上的模块目录,即项目的根目录
# alien.py文件内容name = "alien"
如上文件导入方式,在终端环境下是可以运行的,但是在pycharm里面是不行的,优化后的方案如下:
import sys,osbusiness_path = os.path.join(os.getcwd(), "..") # Business模块路径bs_path = os.path.join(os.getcwd(), "../Business") # BS模块路径sys.path.append(bs_path)sys.path.append(business_path)from Business.BS import alienprint(alien.name)
把父模块和子模块都添加到环境变量中,然后在pycharm和终端里面,都可以直接运行了。
# __init__.py文件对应的内容__all__ = ['buy', "sell"]# 如果没有这句,是不能直接使用from Business import *的# 只能把每个文件都写出来,例如from Business import buy, sell等等
有关__init__.py文件的作用,详情请参考:
https://blog.csdn.net/mengmengz07/article/details/70238429
# sell.py文件修改后为:stock = "000001"ticker = "000002"market = "SZ"
# buy.py文件修改后为:import sys, osmodule_path = os.path.join(os.getcwd(), "..")sys.path.append(module_path)print(sys.path)from Business.sell import * # 这样就不用把每个变量都写进去了,*代表了所有变量print(stock)print(ticker)print(market)