ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

Python包安装四种方式深度对比:conda、pip、git clone与源码安装

Python包安装四种方式深度对比:conda、pip、git clone与源码安装 1. 四种安装方式装的其实是同一个包吗先说个我自己的经历。前阵子给一个新项目配环境项目文档里写需要安装某个依赖库。我二话不说先conda install结果conda源里没有这个包切到pip install装是装上了但import的时候直接报错仔细一看是这个库的版本太老作者新加的接口根本没进去。最后没办法只能git clone从GitHub上拉最新的 main 分支再把源码装进环境里这才跑通。类似的经历你是不是也有过很多刚接触Python的人容易把conda、pip、git clone、源码安装这四种方式当成同一种事情的不同按钮觉得反正都是把包弄进来。但如果你这么理解后面踩的坑会一个接一个。因为这四种方式解决的问题其实不一样分别对应着不同的场景、不同的依赖管理策略、不同的使用人群。我把它们之间的核心区别用一张表整理出来先建立整体框架后面再逐个拆开讲。安装方式获取来源依赖处理典型使用场景版本精确度conda installconda官方或第三方channel自动解析并安装所有依赖包括非Python库数据科学、机器学习项目环境搭建取决于channel里的包版本通常较稳定pip installPyPIPython官方包索引自动解析Python依赖但不管非Python系统库绝大多数纯Python项目、Web框架、脚本工具取决于PyPI上的版本可精确指定git cloneGitHub/Gitee等代码托管平台不处理依赖只拉代码依赖需事后自行安装PyPI上还没有的包、最新开发版、二次开发精确到某个commit或分支源码安装PyPI上的源码包sdist或源码压缩包需要手动安装编译依赖依赖关系通常靠setup.py描述没有预编译wheel的包、需要自定义编译参数精确到你下载的那个版本这张表值得你多看两眼。你会发现conda和pip在依赖处理这一列填的是自动而git clone和源码安装要么不管依赖要么半自动。所以为什么我clone下来的项目跑不起来——这不是你操作问题而是这种方式天生就不管依赖你得自己装。另外一个底层区别要先说清楚conda和pip是包管理器它们的职责是把别人打包好的东西安装到你的环境里而git clone本质上是代码下载工具你拿到的是源代码本身不是可用的包。拿到源码 ≠ 装好包源码还需要经过构建/安装步骤才能真正被Python识别为已安装的库。顺便把另一个高频困惑回答了conda和vscode能放在一起比吗很多人搜conda和vscode的区别。答案是这俩根本不是一回事。conda管的是你的Python环境装在哪里、里面有哪些包vscode是个编辑器它只是用哪个解释器来跑代码需要你手动去指定。实践中的配合方式是你在conda里创建一个环境然后在vscode右下角选择Python解释器时选中这个conda环境对应的路径。这样写代码、跑代码、装包才是在同一个环境里。日常操作就是先conda建环境再打开vscode干活先有环境后有编辑器。2. conda 安装环境隔离与依赖管理的样板间2.1 为什么数据科学圈子偏爱 condaconda和pip之间最要命的区别不在于哪个好用而在于它们处理依赖的层级完全不同。pip处理的是Python包之间的依赖关系比如你装A包A依赖B1.0pip就去PyPI找B装好之后再回来继续装A。但问题是B这个包在安装时可能还需要C库而C库不是Python包是一个系统级的动态链接库比如libssl、libffi。pip默认不管这种系统库它假设你的系统里已经有这些了。如果缺少你装B时会看到一堆error: command gcc failed或者找不到头文件的报错然后一脸懵。conda不是这样的。conda自己维护了一套完整的软件包仓库里面有大量经过验证的二进制包不仅包含Python包本身还包含它们依赖的C/C库、CUDA运行时、OpenBLAS、MKL这类底层组件。conda装一个和深度学习相关的包时会直接把配套的CUDA库也装好你不需要去操心系统里有没有。这就是为什么做数据科学、机器学习的人更愿意用conda——因为这类库的底层依赖是最复杂的。所以记住一句话pip解决的是Python包之间的依赖conda解决的是整个软件运行环境的二进制兼容。2.2 conda create -n 这行命令的完整解读很多教程一上来就让你执行这么一条conda create -n matanyone python3.8 -y conda activate matanyone这条路本身没问题但我发现很多新手不理解每一个参数在干什么导致出了问题不知道怎么排查。逐段拆解一下这条命令conda create表示创建新环境-n matanyone是--name的缩写给这个新环境起名叫matanyonepython3.8指定这个环境里安装Python 3.8版本-y是--yes的缩写意思是所有交互式确认都自动回答yes不然conda会停下来问你Proceed ([y]/n)?。创建好之后conda activate matanyone就是激活这个环境你的终端提示符会变成(matanyone)前缀开头。这时候你再用which python或where python查看Python解释器路径已经指到了conda环境目录下的Python而不是系统自带的那个。为什么非要搞环境隔离我举一个真实例子。之前我在一个旧项目里用了tensorflow 1.x另一个新项目要tensorflow 2.x。如果我都在系统Python里装这俩会互相打架——因为两个版本的库文件可能同名但内容不同import的时候会有各种奇怪报错。用conda建两个独立环境各自装各自的版本互不干扰这才是省心的做法。2.3 国内用户必做的 conda 换源操作这块几乎每个国内用户都会遇到。conda默认的下载源在国外安装大一点的包时速度感人慢得像蜗牛爬有时候还会直接超时失败。我见过不少人在这一步就放弃了以为conda有问题其实只是源的问题。换源操作很简单手动创建或者修改~/.condarc文件Windows下是C:\Users\你的用户名\.condarc写入清华源配置channels: - defaults show_channel_urls: true default_channels: - https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/main - https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/r - https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/msys2 custom_channels: conda-forge: https://mirrors.tuna.tsinghua.edu.cn/anaconda/cloud pytorch: https://mirrors.tuna.tsinghua.edu.cn/anaconda/cloud配置好之后用conda clean -i清除索引缓存再conda install python3.11这种操作就会快很多。实测从国外默认源装一个包含大量依赖的包可能要好几分钟换清华源之后基本上秒级下载。另外提醒一点如果你是帮别人配置环境或者是自己在多台机器上来回折腾建议备份一下conda配置别每次重装系统再手动配一遍。常用的做法是# 导出当前环境的全部包列表 conda list --export requirements_conda.txt # 或者导出完整环境配置包含Python版本和所有依赖 conda env export environment.yml然后换机器后用conda env create -f environment.yml一条命令重建整个环境。这个习惯能帮你省下大量重复配环境的体力活。2.4 conda 环境里的 pip 陷阱这个坑我踩过不止一次现在每次都得提醒自己。在conda环境里是可以使用pip install的而且命令确实会执行成功。但是pip和conda对环境的认知不完全一样conda环境激活后pip确实会把包装进当前conda环境的site-packages里——前提是你用的是这个环境里的pip而不是系统的pip。如果你的终端里执行which pip显示的是/usr/bin/pip或C:\Python\Scripts\pip.exe那说明你现在用的不是conda环境里的pip包装到系统环境里去了。等你切回conda环境import这个包依然会报ModuleNotFoundError。怎么规避两个习惯激活conda环境后先执行which pipWindows是where pip确认路径在conda环境目录下。更保险的办法直接用python -m pip install 包名这样永远是用当前Python解释器对应的pip去装不会装错地方。还有个更隐蔽的问题就是conda和pip混用导致的环境膨胀。conda不认识pip装进去的包pip也不认识conda的依赖解析逻辑。如果两者频繁混用环境的依赖树会越来越乱最终可能出现conda uninstall某个包之后pip之前装的依赖变成了孤儿或者反过来。比较稳妥的顺序是优先用conda installconda源里没有的再pip install一旦开始pip装了就不要回头用conda去删那些有pip依赖的包。删除整个虚拟环境的命令也顺便说一下conda remove -n matanyone --all--all表示连环境目录一起删干净。如果只是删环境里某个包用conda remove -n 环境名 包名。3. pip 安装最常见但坑也最多3.1 pip install 到底做了什么pip是Python官方推荐的包管理工具绝大多数Python开发者每天都会用到。但是很多人对 pip install 的理解停留在把包装好这一个模糊概念上遇到问题就不知道怎么排查了。拆开来看pip install 包名执行后大致做了这几件事访问PyPIPython Package IndexPython官方包索引搜索这个包根据当前Python版本、操作系统、系统架构选择合适的发行版本包下载并解压到一个临时目录解析这个包的依赖声明写在它的metadata里然后递归地安装所有依赖把包文件复制到当前Python环境的site-packages目录如果包里有需要编译的C扩展pip会尝试在本机调用编译器现场编译。了解这个流程后你就会明白为什么有时候pip install会报一些奇怪的错。比如报No matching distribution found for 包名说明PyPI上根本没有这个名字的包或者它支持的操作系统/Python版本跟你当前环境不匹配再比如报error: Microsoft Visual C 14.0 is required说明这个包没有预编译好的wheel需要现场编译C扩展而你的Windows机器上缺编译器。3.2 为什么国内源成了标配操作刚才说pip默认访问PyPI而PyPI的服务器在国外。国内网络环境下直连PyPI下载一个几十MB的包可能要等很久甚至直接超时报ReadTimeoutError。所以pip换源在国内基本是必做操作。最简单的临时换源方式直接加-i参数指定镜像pip install 包名 -i https://pypi.tuna.tsinghua.edu.cn/simple这样只对当前这条命令生效。如果你不想每次都写就配置成永久生效。Windows和Linux的配置文件路径不同Windows%APPDATA%\pip\pip.ini也就是C:\Users\你的用户名\AppData\Local\pip\pip.ini这就是之前网上很多人问的 appdata local pip 是什么就是这个目录Linux/macOS~/.pip/pip.conf或~/.config/pip/pip.conf。拿Windows来说如果没有这个文件就新建一个写入[global] index-url https://pypi.tuna.tsinghua.edu.cn/simple [install] trusted-host pypi.tuna.tsinghua.edu.cn常用的国内镜像除了清华源还有阿里云https://mirrors.aliyun.com/pypi/simple、豆瓣https://pypi.douban.com/simple等。我自己的习惯是清华源和阿里云源都存着一个挂了就换另一个。3.3 Windows 下 pip 不认账的常见处理Windows上最经典的一个报错是pip : 无法将“pip”项识别为 cmdlet、函数、脚本文件或可运行程序的名称。请检查名称的拼写如果包括路径请确保路径正确然后再试一次。这个报错的原因很直白系统PATH环境变量里找不到pip的路径。常见解决方案有三种重新打开终端。很多时候你刚装完PythonPATH已经写进去了但终端是在装之前开的不会自动更新环境变量关掉重开通常就解决了。手动检查PATH。系统设置 → 高级系统设置 → 环境变量 → Path确认里面有Python安装目录和它的Scripts子目录比如C:\Users\你的用户名\AppData\Local\Programs\Python\Python311\Scripts。绕开PATH直接用python -m pip。这是我最推荐的兜底方式python -m pip install 包名python -m pip的意思是让Python自己去调用pip模块它不依赖PATH里有没有pip。只要你的Python本身能运行这种方式就一定有效。另外如果是新装的Python连pip都没有可以去官网下载get-pip.py执行python get-pip.py就能装好pip。3.4 预发布版本参数解析pip install -u --pre 到底在装什么热搜里有一行很典型的命令pip install -u --pre comfyui-manager这行命令看着简单但里面有两个参数值得单独讲因为很多人会写错或者不理解。先看-u这个参数确实存在但它是--upgrade的缩写也就是说它和-U等价。让我先纠正一个非常常见的错误很多教程里会写pip install -u --pre这个写法其实有问题——小写的-u在大写敏感的Linux环境下可能会被解析成别的东西真正稳定的写法是-U或者--upgrade。所以这条命令规范写出来是pip install -U --pre comfyui-manager再看--pre。它的意思是允许安装预发布版本也就是alpha、beta、rc这些还没有正式发布的版本。为什么有人会故意装预发布版因为有些工具更新太快正式版stable发布频率跟不上很多新功能、新修复只在预发布版里才有。以comfyui-manager为例它是ComfyUI生态里的一个管理插件功能迭代非常频繁网上很多教程在某个时间点写用这条命令装是因为当时确实需要装pre-release才能用上新特性。等到正式版追上来--pre参数就可能没那么必要了。实际使用中--pre是一个很实用但容易被忽略的参数。如果你发现某个包装完之后功能不全或者文档里提到的某一项你在代码里找不到可以先检查一下是不是有更新版本还没发布然后加上--pre试试看。当然装预发布版的代价是可能遇到不稳定、有bug的情况生产环境慎用但在开发环境里这往往是抢先体验新功能的唯一途径。4. git clone 安装拿到的不是包是源码4.1 先搞清楚git clone和pip的本质区别有一类问题在网上被反复提问为什么我用pip装了一个包运行还是报错找不到模块为什么PyPI上搜不到作者说的那个包名这些问题的答案往往指向同一个事实PyPI上的包和GitHub上的仓库是两个不同的分发渠道。PyPI是Python包的官方发布平台所有经过打包、发布流程的包才能在上面看到。而GitHub是源代码托管平台很多项目在开发早期、还没发布到PyPI的时候代码只存在于GitHub仓库里。比如你在GitHub上看到一个很实用的库作者只在README里写了To install, run pip install xxx但你一搜PyPI发现根本没有——很可能是因为作者还没来得及发布或者版本还很新、只发了main分支上的代码。这时候你就得用git clone把源码直接拉下来再手动安装。还有一个典型场景是openclaw这类工具的安装脚本——它会在安装过程中问你是用包管理器安装还是用git方式从main分支拉取选git方式就相当于指定了我要装最新开发版。另外注意git clone和git pull不是一回事。clone是把远程仓库完整地复制到本地一般只需要执行一次pull是拉取远程仓库的最新提交来更新你本地已有的仓库。概括说clone是第一次拿代码pull是后续同步更新。4.2 git clone 安装Python包的标准流程git clone安装Python包的标准做法其实也就是三步git clone https://github.com/用户名/仓库名.git cd 仓库名 pip install .pip install .这个命令会读取当前目录下的setup.py、pyproject.toml或setup.cfg根据里面的描述来安装这个包。它相当于把这个源码目录当成一个本地包来安装会把包文件复制到site-packages还会解析和安装依赖。有时候你 clone 下来的目录名和最终import的名字不一致这是正常的。比如目录叫ComfyUI-Manager但实际import的是comfyui_manager具体要看setup.py里的name字段。装完之后你可以用pip show 包名来确认安装情况。这里有一个判断标准能帮你快速决定该用pip从PyPI装还是git clone这个包在PyPI上有没有有就优先pip install省心PyPI上没有或者版本太老缺功能GitHub上有源码那就git clone pip install .你需要在这个包的基础上改代码直接clone下来改没必要装进site-packages开发的时候把项目根目录加到sys.path就行。4.3 git clone失败HTTP认证、网络问题与右键菜单git clone这块网上问得最多的是三类问题都在热搜里出现了逐个说。第一类git使用http不能clone。如果你执行的命令是git clone https://github.com/xxx/xxx.git但仓库是私有的或者需要权限就会遇到HTTP认证失败、提示输入用户名密码的情况。现在GitHub已经不支持直接用账号密码走HTTPS认证了你要用自己的用户名加上Personal Access Token个人访问令牌来当密码。生成token的位置在GitHub: Settings - Developer settings - Personal access tokens - Tokens (classic)然后Generate new token勾选repo权限范围复制生成的那串字符。clone私有仓库时用git clone https://用户名:你的tokengithub.com/用户名/仓库名.git执行完之后Git会把你的凭据缓存到Windows凭据管理器或Linux的凭证存储里下次再访问同一个域名就不用重复输入了。如果你不想每次把token放在URL里也可以在Windows上配置credential manager。Git for Windows安装时自带了git-credential-manager第一次clone私有仓库时会在弹出的Windows凭据管理器窗口里填入用户名和token之后自动记住。第二类网络问题导致clone失败。git clone失败网络问题是热搜高频词。这种现象通常是clone大仓库、或者网络环境不好时clone到一半报RPC failed; HTTP 500 curl 22 The requested URL returned error: 500之类。解决办法有几种调大HTTP缓冲git config --global http.postBuffer 524288000做浅克隆只拉取最新一次提交不要完整历史git clone --depth 1 https://github.com/用户名/仓库名.git浅克隆对某些只需要最新代码的场景特别实用比如你要装一个开发版的包根本没必要时拉全所有历史提交。如果仓库特别大还可以只拉某个分支或指定tag。第三类安装git后右键没有git clone。这个热搜词我见过很多次它其实是个误解。Git安装后右键菜单Windows资源管理器里默认有Git Bash Here和Open Git GUI here但不会有git clone这个选项。git clone是命令行操作你需要在Git Bash、PowerShell或者CMD里手动输入命令。如果你想从某个仓库地址clone就打开终端切换到你想存放代码的目录再执行git clone 仓库地址。4.4 clone下载之后常见的一个装完却用不了坑最后补充一个clone安装的高频后续问题。很多人clone完项目执行了pip install .也提示Successfully installed但写代码时import还是失败。这个问题的原因通常是当前终端激活的Python环境和执行pip install时用的是同一个环境吗很多人clone完仓库后忘记激活目标conda环境或虚拟环境直接在系统Python里pip install了结果包装到了系统环境里自己项目用的却是另一个虚拟环境。解决方法就是老老实实先激活目标环境再执行安装安装完用pip show 包名确认安装路径是不是在当前环境下。5. 源码安装终极兜底方案与编译链路5.1 什么时候必须走源码安装源码安装这个词听起来很远古像早期Linux装软件的方式但实际上它在Python生态里仍然有不可替代的位置。前面讲的git clone安装本质上也是源码安装的一种——因为clone下来的是源码需要本地构建。但更传统的源码安装指的是从PyPI下载源码包sdist或者从网上拿到一个.tar.gz源码压缩包然后解压、构建、安装。这两种路径有一个共同点都是在本机现场编译而不是直接下载预编译好的wheel或conda二进制包。什么时候必须走这条路三类典型情况PyPI上没有预编译wheel。有些包只发布了源码包sdistpip install会尝试现场编译。如果编译工具链齐全能装成功如果缺编译器就会出现各种报错。需要改源码里的参数。比如有些C扩展库默认编译参数不适合你的机器需要修改源码或者Makefile后重新编译。需要安装非常规版本的软件。热搜里有centos源码安装lldp、linux系统安装python这类词都是同一个思路——系统包管理器里的版本太老或者包管理器里根本没有这个软件只能从源码编译。Linux系统安装Python时尤其常见很多老版本系统自带的是Python 2或者Python 3.6你想用新版本但又不想动系统的包管理器就下载Python源码自己configure、make、install。5.2 一套通用的源码安装流程以安装一个典型的Python包源码为例完整链路是这样的# 1. 下载源码压缩包并解压 wget https://example.com/package-1.2.3.tar.gz tar -zxvf package-1.2.3.tar.gz cd package-1.2.3 # 2. 检查构建配置纯Python包可以跳过 ./configure --prefix/usr/local # 3. 编译如果有C扩展 make -j4 # 4. 安装 make install但如果你是给Python装包更常见的是用pip来驱动源码构建省去手动configure的麻烦# 在源码目录里 python setup.py build python setup.py install或者直接用pippip install .在Windows上源码编译的难度比Linux大不少。最经典的问题就是报错error: Microsoft Visual C 14.0 is required。解决办法是安装Visual Studio Build Tools勾选使用C的桌面开发工作负载。装了之后大部分带有C扩展的包就能顺利编译了。如果你的包是纯Python代码没有C扩展源码安装会更简单本质上就是把代码文件复制到site-packages目录。这种情况下用python setup.py install和pip install .效果相同但我更推荐后者——因为pip会对依赖关系做校验和记录的更完整。5.3 编译失败的高频原因和排查顺序源码编译失败的报错五花八门但原因其实高度集中在这么几个点按照可能性排个序缺少Python头文件。在Linux上这对应python3-dev或python3-devel包在Windows上对应的是编译工具里的Python开发支持。报错信息通常是Python.h: No such file or directory。缺少系统依赖库。比如libssl-dev、libffi-dev、libjpeg-dev这些在编译一些特定包时会被用到。报错通常是fatal error: openssl/ssl.h: No such file or directory之类。编译器版本太老或与Python版本不匹配。Python 3.11之后对C标准有要求老版本GCC可能报奇怪的模板错误。构建环境不对。在系统全局环境里也没有在虚拟环境里编译成功率高——这是很多新手想不到的一点。在conda环境或venv里源码安装权限问题少路径也不会搞乱。所以如果你的源码安装失败了按这个顺序排查会比乱搜一堆错误代码高效得多先确认Python头文件在不在 → 再确认编译器可用 → 再确认系统依赖库在不在 → 最后把构建环境切到虚拟环境里重试。这里必须强调一个建议源码安装尽量在虚拟环境里做不要直接装到系统全局Python里。源码安装不像conda或pip那样有完善的卸载和依赖追踪机制直接装全局环境将来想卸载容易留下残留文件想升级版本也可能和别的包冲突。虚拟环境把这些问题隔离在一个沙盒里乱了删掉重建就行。5.4 源码安装成功却 import 失败检查这三个地方好不容易编译安装成功了结果进入Python一import又报ModuleNotFoundError这种体验特别让人崩溃。遇到这种情况依次检查三个位置site-packages目录里有没有包文件。执行python -c import site; print(site.getsitepackages())看输出路径是不是当前环境的site-packages。有没有编译产物残留。源码目录下经常会有build/目录残留如果这些残留文件和当前Python版本不匹配可能导致import时加载到了错的.so文件。清理办法是把源码目录里的build目录删掉重新安装。sys.path有没有包含包的安装位置。如果你装到了一个自定义路径比如--prefix/some/path但你的Python解释器不知道这个路径import自然会失败。解决方式是设置PYTHONPATH环境变量指向这个路径或者干脆用pip install .让它装到标准site-packages少给自己找麻烦。6. 选型次序与一个帮你少踩坑的决策习惯四种方式讲完之后回到最开始的问题到底什么时候用哪种我的个人经验是按这个顺序做决策能用conda就优先conda尤其你是在做数据科学、机器学习相关的事情conda帮你处理了大部分系统级依赖省心程度最高conda源里没有的包用pippip的包数量最多、更新最快PyPI上也找不到或者版本太旧需要最新代码的git clone pip install .git clone也没有或者需要改编译参数的源码安装兜底。这个顺序的本质是从别人帮你解决依赖到你自己负责依赖的逐渐过渡。越靠前越省心越靠后越自由但也越需要你懂底层。还有一个我实际用下来特别舒服的习惯建议你养起来把每个项目的环境都固化成配置文件别依赖记忆。conda环境用conda env export environment.yml导出之后再conda env create -f environment.yml重建pip包用pip freeze requirements.txt导出再pip install -r requirements.txt重装。这样你在哪台机器上都能一键复制出同样的环境不用每次重新纠结我当时到底pip装了什么、conda装了什么。我自己踩过最大的一次坑就是项目跑了几个月之后某天在服务器上从零搭建环境发现怎么都复现不了原来的版本组合最后只能靠git log和commit历史里藏的安装记录一点点对回去浪费了整整一晚上。从那之后environment.yml 和 requirements.txt 就成了每个项目的标配文件。这四种安装方式没有谁比谁高级只有谁比谁适合当前的场景。理解了它们的底层差异再遇到装包报错你就不会一脸懵了——你知道问题是出在依赖解析、网络、编译工具链还是环境隔离层面基本能一下定位到方向。这比记住一堆命令要重要得多。
返回列表