1. 为什么多环境管理是AI编程的第一道坎搞AI编程的人十个里有八个被Python环境坑过。你兴冲冲地从某个技术社区抄来一段模型推理代码pip install一把梭结果跑起来直接报错——ImportError: cannot import name xxx from numpy。再一看原来你半年前装的那个数据分析项目把numpy锁死在1.19版本而眼前这段代码需要numpy 1.24以上的新API。这时候你有两个选择要么把旧项目的依赖全升一遍赌它不会崩要么新建一个环境从头装。选前者的人往往在半小时后对着满屏红色报错陷入沉思。这就是Python多环境管理要解决的核心问题不同项目对同一个包的版本需求可能互相冲突而全局环境只能容纳一个版本。Anaconda或者更轻量的Miniconda就是目前AI编程领域最主流的解决方案之一。它不仅能隔离Python解释器本身还能隔离底层C库、CUDA工具链这些pip管不了的东西——这一点对搞深度学习的人来说太关键了。这篇文章适合谁看如果你正在用Python做AI相关的开发不管是调模型、跑实验还是做数据处理只要你遇到过“装了这个包那个就坏”的情况或者你刚入手一台新机器准备搭AI开发环境那接下来的内容就是为你准备的。我会从环境隔离的底层逻辑讲起一步步带你用Anaconda把多环境管理这件事彻底理顺包括创建、切换、导出、迁移、清理的完整流程以及那些官方文档里不会写的踩坑经验。2. 环境隔离的底层逻辑与Anaconda的定位2.1 全局环境为什么必然出问题Python的包管理机制决定了当你执行pip install numpy时它默认把包装到当前Python解释器对应的site-packages目录下。如果你只有一个Python解释器那所有项目共享同一个site-packages这就是所谓的“全局环境”。问题在于site-packages里同一个包只能存在一个版本。numpy 1.19和numpy 1.24的目录名都是numpy装新的就会覆盖旧的。有人会说那我用pip install numpy1.19和pip install numpy1.24分别装到不同目录行不行理论上可以但你需要手动管理PYTHONPATH而且很多包的依赖关系是嵌套的——A包依赖numpy 1.19B包依赖numpy 1.24你手动指定路径也解决不了运行时动态链接的问题。更不用说像PyTorch这种包它依赖特定版本的CUDA运行时库这些库的路径是编译时写死的不是改个环境变量就能切换的。所以结论很明确全局环境只适合“一台机器只做一个项目”的场景但凡你有两个以上项目就必须做环境隔离。2.2 Anaconda和Miniconda到底选哪个Anaconda和Miniconda的关系可以理解为“全家桶”和“单点套餐”。Anaconda预装了conda、Python、以及几百个常用的科学计算包numpy、scipy、pandas、jupyter等安装包大概3到5个G。Miniconda只包含conda和Python安装包不到100M其他包按需安装。我的建议很直接如果你刚开始学AI编程用Anaconda省得一个个装基础包如果你已经有明确的项目需求或者磁盘空间紧张用Miniconda。我自己两台机器上都是Miniconda因为Anaconda预装的那些包版本往往偏旧而且很多我根本用不到反而增加了环境冲突的概率。安装过程这里不展开官网下载对应系统的安装包一路下一步就行。唯一需要注意的是安装时勾选“Add to PATH”这个选项虽然官方不推荐但不勾选的话后续在终端里调用conda会麻烦很多。如果你没勾选也不用重装手动把conda的安装路径加到系统环境变量里就行。2.3 conda和pip的分工与边界这是新手最容易混淆的地方。conda和pip都是包管理器但它们管理的范围不一样。conda能管理Python包也能管理非Python的二进制依赖比如CUDA、MKL数学库、编译器工具链。pip只能管理Python包而且它不管二进制依赖装PyTorch的时候如果CUDA版本不对pip装完照样跑不起来。那什么时候用conda什么时候用pip我的经验法则是优先用conda装numpy、scipy、pytorch、tensorflow这些有复杂二进制依赖的包conda会帮你把CUDA、MKL这些底层库一起搞定。conda找不到的用pip一些小众的、纯Python的包conda源里可能没有这时候用pip装。绝对不要混用在同一个环境里不要一会儿conda install一会儿pip install同一个包否则conda的依赖解析会乱掉。如果非要混用先用conda装完所有能装的最后再用pip补漏。注意在conda环境里用pip时一定要确认pip指向的是当前环境的pip而不是全局的pip。可以用which pipLinux/Mac或where pipWindows检查一下路径是否在当前环境目录下。3. 从零搭建一个AI开发环境的完整实操3.1 创建环境的正确姿势创建环境的基本命令是conda create -n 环境名 python版本号。比如我要建一个PyTorch 2.0的环境Python版本选3.10conda create -n torch2 python3.10这里有几个细节值得展开。第一环境名不要用中文、空格和特殊字符用英文加数字和下划线最稳妥。第二Python版本要明确指定不指定的话conda会装它默认的最新版而很多AI框架对Python版本有硬性要求——比如PyTorch 2.0支持Python 3.8到3.11你装个3.12就可能没有对应的wheel包。第三如果你知道这个环境要装哪些大包可以在创建时一并指定让conda一次性把依赖解析做完conda create -n torch2 python3.10 pytorch torchvision torchaudio pytorch-cuda11.8 -c pytorch -c nvidia这条命令会直接从PyTorch的官方channel拉取适配CUDA 11.8的版本省去了后续手动配置CUDA的麻烦。当然前提是你的机器有NVIDIA显卡并且驱动版本支持CUDA 11.8。创建完成后用conda activate torch2激活环境。激活后终端提示符前面会出现(torch2)字样表示你当前的所有操作都在这个环境里。退出用conda deactivate。3.2 环境激活失败的常见原因Windows用户经常会遇到conda activate报错说“CommandNotFoundError”。这通常是因为你用的是cmd而不是Anaconda Prompt或者PowerShell没有初始化conda。解决办法有两个一是直接用Anaconda Prompt安装时自带二是在PowerShell里执行conda init powershell然后重启终端。Linux和Mac用户如果用的是zsh而不是bash也需要执行conda init zsh。这个命令的作用是把conda的初始化脚本写到你的shell配置文件里让shell启动时自动加载conda的函数。执行完之后记得source ~/.zshrc或者重开终端。还有一个坑如果你在conda环境里又用python -m venv建了虚拟环境两层环境叠加会导致路径混乱。我的建议是用了conda就不要再套venv二选一即可。3.3 包安装的优先级与版本锁定环境建好之后装包的顺序也有讲究。假设我要装PyTorch、transformers、datasets这三个包。正确的顺序是先用conda装PyTorch因为它有CUDA依赖再用conda装transformers和datasets如果conda源里有的话最后用pip补装conda找不到的包版本锁定方面不要盲目追求最新版。AI领域的包更新极快新版本往往引入不兼容的API变更。我的做法是先查这个包在GitHub上的release notes看看最近几个版本有没有breaking change然后选择一个相对稳定、社区讨论较多的版本。比如transformers4.30到4.35之间API变动不大但4.36改了tokenizer的默认行为很多旧代码会报warning。如果你要复现一篇论文的实验必须严格按照论文附录里的版本号来装。我见过太多人用最新版transformers跑旧论文的代码结果因为tokenizer的padding策略变了指标差了好几个点。4. 环境导出、迁移与团队协作的实战方案4.1 导出环境配置的两种方式当你把一个环境调通之后下一步就是把它“固化”下来方便在其他机器上复现。conda提供了两种导出方式conda env export environment.yml这会导出当前环境的所有包及其精确版本号包括conda和pip安装的。但这个文件有个问题它包含了本地路径和平台相关的信息比如prefix: /home/user/miniconda3/envs/torch2换一台机器直接conda env create -f environment.yml可能会失败。更通用的做法是加--no-builds参数conda env export --no-builds environment.yml这样导出的文件只保留包名和版本号不包含build字符串跨平台兼容性更好。如果你只想导出你手动安装的包不包含依赖可以用--from-historyconda env export --from-history environment.yml这个方式导出的文件最干净但前提是你所有包都是通过conda install装的pip装的包不会被记录。4.2 跨平台迁移的注意事项Linux和Windows之间的环境迁移是最容易出问题的。因为很多包的二进制wheel是平台相关的Linux上的.so文件在Windows上根本用不了。所以跨平台迁移时不要直接复制环境目录而是用environment.yml重建。重建的流程是conda env create -f environment.yml -n 新环境名如果environment.yml里包含了平台相关的包比如pytorch-cuda在目标平台上可能需要换成对应的版本。比如Linux上装的是pytorch-cuda11.8Windows上可能要用pytorch-cuda11.8的Windows版或者干脆用CPU版先跑通流程。还有一个隐藏的坑conda的channel优先级。如果你在environment.yml里指定了-c pytorch -c nvidia但目标机器的conda配置里默认channel是清华源可能会导致包版本对不上。解决办法是在yml文件里显式写出channel或者在创建环境时用--override-channels强制使用指定的channel。4.3 团队协作中的环境规范如果你在一个小团队里做AI项目环境管理必须有一套规范否则“在我机器上能跑”会成为日常。我的建议是每个项目一个environment.yml放在项目根目录下和代码一起提交到Git。environment.yml里锁定主版本号比如numpy1.24而不是numpy避免自动升级到不兼容的版本。README里写清楚环境创建命令包括conda版本要求、是否需要GPU、CUDA版本等。定期更新environment.yml但更新后要在CI里跑一遍测试确保没有引入不兼容的变更。提示如果团队里有人用pip有人用conda可以维护两个文件environment.yml给conda用户requirements.txt给pip用户。但要注意两者的包版本要尽量对齐否则还是会出现行为不一致。5. 环境清理、磁盘管理与性能优化5.1 查看和删除无用环境用久了之后你的机器上可能会堆积十几个环境每个环境占几个G磁盘很快就满了。查看所有环境conda env list删除环境conda env remove -n 环境名但删环境之前先确认这个环境里有没有你还需要的东西。我一般会先激活这个环境跑一下conda list看看装了哪些包确认没有独家的包之后再删。5.2 清理conda缓存conda在安装包的时候会把下载的压缩包缓存在pkgs目录下时间长了这个目录可能占几十个G。清理命令conda clean --all这个命令会清理索引缓存、锁文件、未使用的包和tarball。如果你想保留最近下载的包以便快速重装可以用conda clean --tarballs只清理压缩包保留解压后的包目录。5.3 环境克隆与重命名conda没有直接的重命名命令但可以通过克隆来实现conda create -n 新环境名 --clone 旧环境名 conda env remove -n 旧环境名克隆的好处是新环境会完整复制旧环境的所有包和配置包括pip安装的包。但要注意克隆出来的环境会占用额外的磁盘空间如果只是临时用一下不如直接激活旧环境。5.4 加速conda安装的实用技巧conda默认从国外的源下载包速度可能很慢。换成国内镜像源可以显著提升速度。配置方法conda config --add channels https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/main/ conda config --add channels https://mirrors.tuna.tsinghua.edu.cn/anaconda/pkgs/free/ conda config --set show_channel_urls yes但要注意有些包在镜像源上可能不是最新版或者缺少某些build。如果遇到PackagesNotFoundError可以临时用-c参数指定官方源conda install -c pytorch pytorch另外conda的依赖解析在环境复杂时会很慢。可以用--no-deps跳过依赖检查但这样可能会导致包版本冲突只建议在明确知道自己在做什么的情况下使用。更安全的加速方式是安装libmamba求解器conda install -n base conda-libmamba-solver conda config --set solver libmamba这个求解器比conda默认的快很多尤其是在环境里有几十个包的时候速度提升非常明显。6. 常见问题排查与避坑经验实录6.1 环境激活后Python版本不对有时候你激活了环境但python --version显示的版本和创建时指定的不一致。这通常是因为你的系统PATH里有一个全局的Python它的优先级高于conda环境的Python。解决办法是检查which python的路径如果指向/usr/bin/python而不是~/miniconda3/envs/xxx/bin/python说明conda的环境变量没有正确加载。在Linux/Mac上可以执行conda init后重开终端。在Windows上确保你用的是Anaconda Prompt而不是普通的cmd。如果还是不行可以手动在环境激活后执行export PATH~/miniconda3/envs/xxx/bin:$PATHLinux/Mac或set PATH~/miniconda3/envs/xxx/bin;%PATH%Windows。6.2 pip和conda混用导致的依赖冲突这是最经典的问题。你在conda环境里用pip装了一个包结果conda的依赖解析器不认这个包后续用conda装其他包时可能会把它覆盖掉或者报依赖冲突。排查方法是先用conda list看看这个包是不是通过pip装的pip装的包在conda list里会显示为pip。如果是而且你后续还要用conda装包建议先用pip卸载这个包再用conda重装。如果conda源里没有这个包那就尽量把其他包都用conda装完最后再用pip装它。注意conda list里显示的pip包其版本号可能和pip show显示的不一致因为conda记录的是安装时的元数据而pip可能后续更新过。以pip show为准。6.3 CUDA版本与PyTorch不匹配这是深度学习环境里最高频的问题。症状是torch.cuda.is_available()返回False或者运行时报CUDA error: no kernel image is available for execution on the device。排查步骤用nvidia-smi查看驱动支持的CUDA版本右上角显示的是驱动支持的最高CUDA版本。用conda list | grep cudatoolkit查看当前环境安装的CUDA版本。确认PyTorch编译时用的CUDA版本和当前环境一致。如果驱动支持的CUDA版本低于PyTorch需要的版本要么升级驱动要么装CPU版的PyTorch。如果驱动支持但环境里装错了重新用conda装对应版本的PyTorchconda install pytorch torchvision torchaudio pytorch-cuda11.8 -c pytorch -c nvidia6.4 环境磁盘占用过大一个包含PyTorch和transformers的环境轻松占5到10个G。如果你有多个这样的环境磁盘很快就满了。除了前面说的conda clean --all还可以删除环境里不需要的包比如conda remove -n 环境名 包名。用conda list --explicit spec-file.txt导出精确的包列表然后删掉环境需要时再重建。把不常用的环境导出为yml文件后删除需要时再创建。6.5 环境迁移后包找不到用environment.yml重建环境后有时候会报某个包找不到。这通常是因为这个包是通过pip装的但environment.yml里没有记录因为用了--from-history。这个包在目标平台的conda源里没有对应的build。channel配置不一致。解决办法是在environment.yml里手动加上pip安装的包或者单独维护一个requirements.txt。如果某个包在目标平台确实没有可以尝试用pip装或者找替代包。6.6 常见问题速查表问题现象可能原因排查命令解决方案conda activate报错shell未初始化conda init执行init后重开终端python版本不对PATH优先级问题which python检查环境变量顺序pip包被覆盖conda/pip混用conda list统一用conda或最后用pipCUDA不可用版本不匹配nvidia-smiconda list重装对应版本PyTorch磁盘占用大缓存和环境堆积du -sh ~/miniconda3conda clean --all 删无用环境迁移后包缺失yml不完整conda env export补全pip包或改用--no-builds安装速度慢源在国外conda config --show channels换国内镜像源依赖解析慢求解器效率低conda info安装libmamba求解器7. 我个人的环境管理习惯与工具链搭配用了五六年conda之后我形成了一套自己的习惯这里分享出来供参考。第一base环境只装conda本身和jupyter。很多人习惯在base里装各种包结果base越来越臃肿最后连conda自己都更新不了。我的base环境里只有conda、mamba、jupyterlab其他一律不装。第二每个项目一个环境环境名和项目名对应。比如项目叫text-classifier环境就叫text-classifier。这样一看环境列表就知道哪个环境对应哪个项目不用猜。第三environment.yml和requirements.txt同时维护。environment.yml给conda用户requirements.txt给pip用户。两个文件里的版本号尽量对齐避免行为不一致。第四定期清理但保留最近三个月的环境。超过三个月没碰的环境先导出yml文件然后删掉。需要的时候再重建反正有yml文件在重建也就几分钟的事。第五用mamba替代conda做日常操作。mamba的求解器快很多命令和conda几乎一样只是把conda换成mamba。安装mamba很简单conda install -n base mamba -c conda-forge之后就可以用mamba create、mamba install、mamba env list等命令体验会好很多。第六Jupyter内核要手动注册。在conda环境里装了jupyter之后默认的kernel可能还是base环境的Python。需要手动注册conda activate 环境名 pip install ipykernel python -m ipykernel install --user --name环境名 --display-name显示名称这样在Jupyter里就能看到这个环境的kernel了。如果后续环境里的包有更新不需要重新注册kernel重启Jupyter即可。第七用conda-pack打包环境迁移到离线机器。有些场景下目标机器不能联网这时候可以用conda-pack把整个环境打包成一个tar.gz文件复制过去解压就能用conda install -c conda-forge conda-pack conda pack -n 环境名 -o 环境名.tar.gz在目标机器上解压后执行source bin/activate就能激活。这个方式比重建环境快得多但要注意目标机器的操作系统和架构要一致。最后再分享一个小技巧如果你不确定某个包该用conda还是pip装可以先在conda的搜索里查一下conda search 包名如果搜到了优先用conda。如果没搜到再用pip。这个简单的习惯能帮你避免大部分依赖冲突问题。
阅读完成 · 觉得有帮助?