为什么使用sys.path.append(path)而不是sys.path.insert(1,path)?
编辑:基于Ulf Rompe的评论, 重要的是你使用“1”而不是“0” ,否则你会打破sys.path 。
我一直在做python了一段时间(一年多),而且我总是困惑,为什么人们推荐你使用sys.path.append()
而不是sys.path.insert()
。 让我来certificate一下。
比方说,我正在研究一个名为PyWorkbooks(安装在我的计算机上)的模块,但是我正在同时使用一个包含PyWorkbooks的不同模块(比方说PyJob)。 当我在PyJob上工作时,我在PyWorkbooks中发现错误,所以我想导入一个开发版本。
有两种方法可以同时工作(例如,我可以将PyWorkbooks项目放在PyJob中),但是有时我仍然需要使用path。 但是, 我不能简单地执行一个sys.path.append()
到PyWorkbooks所在的文件夹 。 为什么? 因为python会先find我安装的PyWorkbook!
这就是为什么你必须做一个sys.path.insert(1,path_to_dev_pyworkbooks)
综上所述:
sys.path.append(path_to_dev_pyworkbooks) import PyWorkbooks # does NOT import dev pyworkbooks, imports installed one
要么:
sys.path.insert(1, path_to_dev_pyworkbooks) # based on comments you should use **1 not 0** import PyWorkbooks # imports correct file
这在过去对我造成了一些困扰,如果我们(作为一个社区)开始推荐sys.path.insert(1, path)
,就好像你正在手动插入一个我认为是的path安全地说,这是你想要使用的path!
或者我有什么问题? 这是一个困扰我的问题,我希望它公开!
如果你有一个包/模块的多个版本,你需要使用virtualenv (强调我的):
virtualenv
是创build独立Python环境的工具。正在解决的基本问题是依赖和版本之一,以及间接的权限。 想象一下你有一个需要LibFoo版本1的应用程序,但是另一个应用程序需要版本2.你怎么能使用这两个应用程序? 如果你把所有东西都安装到
/usr/lib/python2.7/site-packages
(或者你的平台的标准位置),那么很容易导致无意中升级不应该升级的应用程序。或者更一般地说,如果你想安装一个应用程序,并保持它是什么? 如果应用程序正常工作,则其库中的任何更改或这些库的版本都可能会中断应用程序。
另外,如果您不能将软件包安装到全局
site-packages
目录中呢? 例如,在共享主机上。在所有这些情况下,
virtualenv
可以帮助你。 它会创build一个具有自己的安装目录的环境,它不会与其他虚拟环境共享库(也可能不访问全局安装的库)。
这就是为什么人们认为insert(0,
是错误的 – 对于pipe理多个环境的问题,这是一个不完整的解决scheme。
如果您确实需要使用sys.path.insert,请考虑将sys.path [0]保持原样:
sys.path.insert(1, path_to_dev_pyworkbooks)
这可能很重要,因为第三方代码可能依赖于sys.path文档一致性:
在程序启动时初始化,这个列表中的第一个项目path [0]是包含用于调用Python解释器的脚本的目录。
你混淆了追加和前置的概念。 下面的代码是预先考虑的:
sys.path.insert(1,'/thePathToYourFolder/')
它将把新的信息放在你的解释器将要经历的search顺序的开始处(准确的说是第二个)。 sys.path.append()
把东西放在search顺序的最后。
build议你使用像virtualenv
这样的东西,而不是每次手动编写你的包目录到PYTHONPATH
。 为了设置不同的生态系统,将你的站点包和可能的python版本分开,请阅读这两个博客:
-
python生态系统介绍
-
引导python虚拟环境
如果你决定走向环境隔离的道路,你一定会从virtualenvwrapper中受益: http : //www.doughellmann.com/docs/virtualenvwrapper/