Python 虚拟环境是 Python 开发中隔离项目依赖的核心工具。本教程系统讲解从 Python 内置的 venv 到现代化工具 uv 的完整知识体系,帮助读者理解不同工具的设计理念、适用场景和操作方式,最终能够根据项目需求选择最合适的方案。

1. Python 虚拟环境基础

1.1 什么是 venv

venv 是 Python 3.3 及以上版本自带的轻量级虚拟环境管理工具。它的核心作用是为每个项目创建独立的 Python 运行环境,隔离不同项目所需的第三方包版本。

典型场景:项目 A 需要 Django 2.0,项目 B 需要 Django 4.0,如果全局安装会导致依赖冲突,两个项目无法共存。使用 venv 后,每个项目拥有独立的 site-packages 目录,版本冲突自然消除。

我们认为:无论是人还是应用系统,都需要一个干净、集中的工作环境

1.2 venv 基础操作

创建虚拟环境

在项目根目录下打开终端,运行:

python -m venv .venv

环境名称通常叫 venv.venv(加点为隐藏文件夹)。建议使用 .venv,因为它是很多工具(如 uvPoetry)的默认目录名,且不会在文件管理器中显得杂乱。

激活虚拟环境

激活后,安装的包才会进入这个独立环境:

操作系统 命令
Windows (CMD) .venv\Scripts\activate
Windows (PowerShell) .venv\Scripts\Activate.ps1
macOS / Linux source .venv/bin/activate

激活成功后,终端命令行前面会出现 (.venv) 标识。

安装依赖并运行项目

pip install fastapi uvicorn # 安装 fastapi 和 uvicorn 两个依赖
python app.py               # 运行项目

退出虚拟环境

deactivate

1.3 管理项目依赖

在虚拟环境中,使用 pip freeze 导出当前环境的所有包及版本:

pip freeze > requirements.txt

其他人拿到项目后,只需运行以下命令即可安装完全相同的依赖版本:

pip install -r requirements.txt

1.4 重要注意事项

不要将虚拟环境提交到 Git 仓库

虚拟环境体积大且包含系统特定文件,不应纳入版本控制。在项目根目录创建 .gitignore 文件,添加以下内容:

.venv/
venv/

有关于 Git 仓库.gitignore 的内容,你可以前往Git的安装与基本使用教程进行回顾。

不同 Python 版本依赖

venv 只使用创建时指定的 Python 解释器版本。如果需要切换 Python 版本,需要删除 .venv 目录后重新创建。

2. Conda 环境管理详解

我们在Python+FastAPI在Windows环境下创建一个基础后端服务教程中介绍了 Conda 的下载、安装、环境管理等操作,你可以前往回顾,这里主要介绍 Conda 与其他环境管理工具的区别和适用场景。

特性 Conda pip + venv
包来源 Conda 官方仓库(Anaconda.org) PyPI(Python Package Index)
支持语言 跨语言(Python、R等) 仅 Python
管理 Python 版本 可安装/切换不同 Python 版本 只使用系统已安装的 Python
管理非 Python 依赖 可管理 CUDA、OpenBLAS 等底层库 只能通过系统包管理器手动安装
依赖解析 较严格,但可能较慢 较宽松
环境隔离 完整隔离(包括系统路径) Python 级隔离
预编译包 提供预编译二进制(避免编译错误) 部分包需编译(需系统编译器)

3. 现代化工具 uv 详解

3.1 什么是 uv

uv 是由 Astral 团队用 Rust 编写的 Python 包和环境管理工具。

uv 的核心优势在于极快的安装速度(比 pip 快 10-100 倍),以及对现有生态的完美兼容(可以直接读取 requirements.txtpyproject.toml)。

3.2 安装 uv

Windows (PowerShell)

powershell -c "irm https://astral.sh/uv/install.ps1 | iex"

macOS / Linux

# 下载最新版本的 uv 安装脚本
curl -LsSf https://astral.sh/uv/install.sh | sh

# 添加到 PATH 环境变量
echo 'export PATH="$HOME/.local/bin:$PATH"' >> ~/.bashrc
source ~/.bashrc

验证安装:

uv --version

3.3 核心工作流

新建项目(推荐方式)

# 初始化项目,自动生成 pyproject.toml 和 uv.lock
uv init my_uv_project

# init 过程中会默认生成 .gitignore 文件,如果你当前暂不涉及仓库和版本管理,你可以通过参数配置默认不生成该文件:
uv init my_uv_project --vcs none

# 进入项目目录
cd my_uv_project

# 创建虚拟环境(默认在 .venv 目录)
uv venv

# 激活环境(和 venv 完全一样)
.venv\Scripts\activate # Windows
source .venv/bin/activate # macOS / Linux

# 添加依赖(自动更新锁文件,uv.lock 可以锁定实际安装的依赖的精确版本,这里以 fastapi 为例)
uv add fastapi uvicorn

# 安装项目所有依赖(包括开发依赖)
uv sync

# 运行主脚本
uv run python script.py

临时安装包试用(不污染项目)

uv tool run black --check .

3.4 常用命令速查

操作 uv 命令 传统命令对比
创建虚拟环境 uv venv python -m venv .venv
安装依赖 uv add requests pip install requests + 手动更新 requirements.txt
安装所有依赖 uv sync pip install -r requirements.txt
删除依赖 uv remove requests pip uninstall requests + 手动删除
锁定依赖版本 自动生成 uv.lock 手动维护 requirements.txt 或使用 pip freeze
更新所有包到最新 uv sync --upgrade pip install --upgrade -r requirements.txt(无法保证版本一致性)
查看当前环境依赖树 uv tree pip list(不显示层级关系)

3.5 管理不同 Python 版本

uv 可以像 conda 一样自动下载并切换 Python 版本:

# 创建环境时指定 Python 版本(自动下载)
uv venv --python 3.11

# 运行脚本时指定
uv run --python 3.12 script.py

3.6 uv sync 命令执行流程

uv sync 是 uv 最核心的命令之一,它在背后完成了五个步骤:

  1. 读取 pyproject.toml:获取项目依赖声明
  2. 处理 uv.lock: - 无锁文件:解析依赖树,生成新的 uv.lock - 有锁文件:对比 pyproject.toml 的变化,按需更新锁文件
  3. 准备虚拟环境:自动创建或复用 .venv 目录
  4. 并行下载依赖:所有包同时下载,利用缓存加速
  5. 安装到虚拟环境:按依赖树顺序安装,保证版本一致
graph LR subgraph Start["开始"] A[执行 uv sync] end A --> B[读取 pyproject.toml] subgraph Decision["条件判断"] direction LR C{检查是否有
uv.lock?} end B --> C C -->|有| D[读取 uv.lock] C -->|无| E[解析依赖树
生成 uv.lock] subgraph Processing["依赖处理"] direction LR F[对比变化
更新锁] G[创建/校验
.venv] end D --> F E --> G subgraph Installation["安装阶段"] H[并行下载依赖] I[安装到
虚拟环境] end F --> G G --> H --> I I --> J[完成] style A fill:#e8f4f8,stroke:#1a6b8a,stroke-width:2px style C fill:#fff3cd,stroke:#856404,stroke-width:2px style D fill:#d4edda,stroke:#155724,stroke-width:2px style E fill:#d1ecf1,stroke:#0c5460,stroke-width:2px style H fill:#f8d7da,stroke:#721c24,stroke-width:2px style I fill:#d4edda,stroke:#155724,stroke-width:2px style J fill:#e8f4f8,stroke:#1a6b8a,stroke-width:2px

4. pyproject.toml 配置指南

4.1 pyproject.toml 的生成方式

pyproject.toml 是现代 Python 项目的标准配置文件,统一了项目元数据、构建系统和依赖声明。

使用 uv init 可以自动生成 pyproject.toml

uv init my_project  # 初始化项目
cd my_project       # 进入项目目录

此时 uv 会自动创建 pyproject.toml 文件,内容如下:

[project]
name = "my_project"
version = "0.1.0"
description = "Add your description here"
readme = "README.md"
requires-python = ">=3.8"
dependencies = []

只需要手动补充 descriptiondependencies 等字段即可。

4.2 完整配置文件示例

[project]
name = "my_project"
version = "0.1.0"
description = "A simple web API"
authors = [
    {name = "Your Name", email = "you@example.com"}
]
license = {text = "MIT"}
readme = "README.md"
requires-python = ">=3.8"
dependencies = [
    "fastapi>=0.100.0",
    "uvicorn>=0.23.0",
    "requests>=2.31.0",
]

[project.optional-dependencies]
# 可选依赖组,安装时使用 uv sync --extra dev
# 与 [tool.uv] dev-dependencies 的区别:
# - optional-dependencies 是 PEP 735 标准,其他工具(pip, Poetry 等)也支持
# - tool.uv.dev-dependencies 是 uv 特有配置,仅 uv 识别
dev = [
    "pytest>=7.0.0",
    "black>=23.0.0",
    "ruff>=0.1.0",
]

[build-system]
requires = ["setuptools>=61.0"]
build-backend = "setuptools.build_meta"

[tool.uv]
dev-dependencies = [
    "pytest>=7.0.0",
]

4.3 核心字段说明

字段 含义 是否必填
name 项目名称(PyPI 上要唯一) 必填
version 版本号(遵循语义化版本) 必填
description 简短描述 必填
requires-python 支持的 Python 版本范围 推荐
dependencies 生产环境依赖包列表 推荐
optional-dependencies 可选依赖(如测试、开发工具) 可选
authors / license 作者和许可证信息 可选(开源项目推荐)

4.4 dependencies字段的快速补全

我们通过 uv add 命令添加依赖后,相关依赖及版本信息会自动添加到 pyproject.toml 中,无需手动添加。

4.5 关于 pyproject.toml 的常见问题

问:单文件脚本需要 pyproject.toml 吗?

不需要。直接用 uv run script.py,它会自动管理依赖,无需 pyproject.toml

问:pyproject.toml 和 requirements.txt 能共存吗?

能。uv sync 会以 pyproject.toml 为准,requirements.txt 会被忽略。但 uv pip install -r requirements.txt 仍然支持,兼容旧项目。

问:没有 pyproject.toml 能用 uv sync 吗?

不能,uv sync 必须依赖 pyproject.toml。但你可以用 uv pip install 替代(兼容 pip 模式),只是享受不到锁机制。

5. 工具选型决策指南

5.1 决策流程图

graph LR subgraph Start["决策开始"] A[你的需求是什么?] end A --> B{是否需要
管理非 Python 依赖?} subgraph Branch1["分支1: 需要非Python依赖"] direction LR C{是否数据科学/
ML项目?} end B -->|是| C C -->|是| D[使用 Conda] C -->|否| E[考虑 Conda 或
系统包管理器 + venv] subgraph Branch2["分支2: 纯Python项目"] direction LR F{是否需要
切换Python版本?} end B -->|否,纯Python| F F -->|是| G[使用 Conda 或 uv] F -->|否| H{是否追求
最快速度?} subgraph Branch3["分支3: 纯Python且
无需切换版本"] direction LR I[使用 uv] J[使用 venv] end H -->|是| I H -->|否| J style A fill:#e8f4f8,stroke:#1a6b8a,stroke-width:2px style B fill:#fff3cd,stroke:#856404,stroke-width:2px style C fill:#fff3cd,stroke:#856404,stroke-width:2px style D fill:#d4edda,stroke:#155724,stroke-width:2px style E fill:#f8d7da,stroke:#721c24,stroke-width:2px style F fill:#fff3cd,stroke:#856404,stroke-width:2px style G fill:#d4edda,stroke:#155724,stroke-width:2px style H fill:#fff3cd,stroke:#856404,stroke-width:2px style I fill:#c3e6cb,stroke:#155724,stroke-width:2px style J fill:#e2e3e5,stroke:#383d41,stroke-width:2px

5.2 工具对比速览

特性 venv Conda Poetry uv
安装包体量 轻量 较重(Miniconda ~50MB) 轻量 轻量
Python 版本管理 不支持 支持 支持(1.2+) 支持
非 Python 依赖 不支持 支持 不支持 不支持
跨语言支持 不支持 支持 不支持 不支持
锁文件 不支持 可选 支持 支持
依赖解析速度 中等 极快
学习曲线 中等 中等
适合数据科学 不适合 适合 一般 一般(配合 pip)

5.3 选型建议

场景 推荐工具 理由
数据科学 / 机器学习 Conda 自动管理 CUDA、MKL 等底层依赖,跨平台一致性好
个人纯 Python 新项目 uv 极速、现代化、学习成本低
AI 项目且用 PyTorch/TensorFlow Conda 自动配置 CUDA,避免手动踩坑
团队协作(非数据科学) uv 锁文件保证版本一致性
老旧服务器跑脚本 venv 够用,无需额外工具
教学 / 新手入门 Conda 预装所有常用包,开箱即用
轻量级 Web 后端 uv 速度快,依赖管理清晰
追求极致速度 uv Rust 实现,安装快 10-100 倍

6. 总结

6.1 核心内容回顾

  • venv 是 Python 内置的轻量级虚拟环境工具,适合基础需求和简单项目
  • Conda 是跨语言的环境管理方案,特别适合数据科学和需要非 Python 依赖的场景
  • uv 是新一代极速工具,用 Rust 编写,速度比 pip 快 10-100 倍
  • pyproject.toml 是现代 Python 项目的标准配置文件,统一管理项目元数据和依赖
  • 工具选型应根据项目类型、团队规模和具体需求综合决策

6.2 常见问题与解答

问:Conda 和 pip 可以混用吗?

可以,但有最佳实践:优先用 conda 安装,conda 没有的包再用 pip 安装。导出环境时用 conda env export --from-history 只保留显式安装的包,避免版本冲突。

问:uv sync 和 pip install -r requirements.txt 有什么区别?

uv sync 基于 pyproject.tomluv.lock 工作,能保证跨环境的版本一致性。pip install -r requirements.txt 只是按列表安装,不会自动处理依赖的依赖版本锁定。

问:如何从 requirements.txt 迁移到 uv?

创建 pyproject.toml 并将依赖填入 dependencies 列表,然后运行 uv sync。uv 会自动生成 uv.lock 并安装所有依赖。

问:团队协作应该选哪个工具?

团队协作的核心需求是版本一致性。推荐使用 uv,它能通过锁文件保证所有开发者使用完全相同的依赖版本。