Python虚拟环境¶
什么是虚拟环境¶
虚拟环境是一个独立的Python环境, 它有自己的Python解释器、库和包, 与系统全局环境隔离, 避免不同项目之间的依赖冲突.
部分系统甚至不允许在全局环境中安装第三方包(比如 Arch Linux), 此时就必须使用虚拟环境来隔离项目依赖.
创建虚拟环境¶
-
使用 Astral uv
uv venv [ENV_NAME] --python=[PYTHON_VERSION] -
使用 Conda
conda create -n [ENV_NAME] python=[PYTHON_VERSION] -
使用 venv
python -m venv [ENV_NAME]
查看虚拟环境信息¶
虚拟环境列表¶
-
uv
项目虚拟环境一般就在目录里的
.venv, uv 没有 conda 那种全局 env 列表.列出本机 Python 解释器:
uv python list列出用
uv tool install装过的 CLI:uv tool list -
conda
conda env list
当前虚拟环境¶
-
uv run(走的是当前项目的.venv, 不是PATH上随便一个可执行文件)uv run python -c "import sys; print(sys.executable)" -
shell
echo $VIRTUAL_ENV which python
提示符里的 (env_name) 只说明 shell 激活了 env_name. which executable 若指向 ~/.local/bin/executable, 跑起来用的就不是 env_name.
看一个 CLI 实际绑的是哪套 Python: which <tool> 之后读第一行 shebang, 例如 #!/home/.../uv/tools/<tool>/bin/python. 然后用这个解释器探测:
~/.local/share/uv/tools/<tool>/bin/python -c "import sys; print(sys.executable); print('\n'.join(sys.path))"
环境隔离¶
import 只看当前这个解释器的 site-packages. 系统里有 requirement, (env_name) 里 import requirement 能过, 都不等于 executable 看得见 requirement.
同一台机器上常见几套互不相通的环境:
| 种类 | 典型位置 | 谁在用 |
|---|---|---|
| 系统 Python | /usr/bin/python, pacman / apt 装的包 | 发行版工具, 不是项目依赖 |
| 项目 venv | 仓库里的 .venv | uv run, source .venv/bin/activate |
| conda env | ~/miniconda3/envs/<name> 一类 | conda activate lab 之后的 python / pip |
| uv tool | ~/.local/share/uv/tools/<工具名>/ | uv tool install 装到 PATH 的 CLI |
| uvx 临时环境 | ~/.cache/uv/ 下的隔离环境 | uvx <工具> 一次性跑; 若该工具已经 uv tool install 过, 常会复用那份 |
uv tool / uvx 是故意隔离的: 每个 CLI 一份 venv, 避免不同工具和项目依赖互相污染.
装错地方¶
ModuleNotFoundError: No module named '<pkg>' 只说明当前这个解释器的 site-packages 里没有 <pkg>. 在别处装一份, 对它无效.
| 执行的命令 | 实际装到哪 | 报错的那个 CLI / 解释器 |
|---|---|---|
uv tool install <tool> | .../uv/tools/<tool>/ | 只看见自己这份 |
uv tool install <pkg> | 又一个独立 tool 环境 | 看不见 |
系统包管理器安装 python-<pkg> | 系统 Python | 看不见 |
已激活的 conda / 项目 venv 里 import <pkg> 能过 | 那份 conda / .venv | 也看不见 |
uv tool install <pkg> 不会把 <pkg> 塞进已经装好的 <tool>; 它只是再开一个以 <pkg> 为名的工具环境.
包装声明漏依赖时也一样: 代码 import <pkg>, metadata 却没写上, 修法仍是往报错的那个环境里补, 而不是往系统或当前 shell 环境里补.
缺依赖时往哪装¶
原则: 谁报错, 就往谁的解释器里装.
# uv 安装的 CLI: 附加依赖用 --with, 不要另装一个同名 tool
uv tool install <tool> --force --with <pkg>
# 一次性跑, 不写入 PATH
uvx --with <pkg> <tool>
# 项目代码 (当前目录的 .venv)
uv add <pkg> # 或 uv pip install <pkg>
# conda
conda activate <env>
pip install <pkg> # 或 conda install <pkg>
--with 把包装进这个工具的 venv, 不把对方的可执行文件装到 PATH. 需要对方的 CLI 时才用 --with-executables-from.