Introduction – What’s a virtual environment and why you need one
When you write Python code you’re not just writing a single script; you’re pulling in libraries, tools, and sometimes different versions of the same library. Installing everything globally (i.e., with pip install straight into your system Python) quickly turns your machine into a tangled mess:
- Project A needs NumPy 1.21, Project B needs NumPy 2.0.
- A system upgrade breaks a script that relied on an older interpreter.
- You can’t share a reproducible “this works on my machine” setup with teammates.
A virtual environment isolates a Python interpreter and its package directory so each project gets exactly what it asks for, and nothing else. This tutorial is aimed at beginners who have written a few scripts and now want a clean, repeatable workflow. We’ll compare three popular tools—venv, conda, and uv—show you how to set each up, and give you a hands‑on example you can run in five minutes.
Part 1 – Core concepts common to all tools
| Concept | What it means | Why it matters |
|---|---|---|
| Interpreter | The python executable that runs your code. |
Different projects may need Python 3.9 vs 3.11. |
| Package directory | Where pip or conda stores installed wheels. |
Keeps dependencies isolated per project. |
| Activation | A shell command that puts the virtual interpreter first on PATH. |
Allows you to run python and pip without typing full paths. |
| Lock file | A machine‑readable list of exact package versions (requirements.txt, environment.yml, uv.lock). |
Guarantees reproducibility across machines. |
All three tools provide these basics, but they differ in how they manage them, what extra features they bring, and how much they rely on external binaries.
Part 2 – venv – the built‑in, zero‑dependency option
When to choose venv
- You already have a working Python installation (3.3+).
- You want the simplest possible workflow, no extra installers.
- Your project only needs pure‑Python packages or wheels available on PyPI.
Setup steps
# 1️⃣ Create a new directory for your project
mkdir my_venv_project && cd my_venv_project
# 2️⃣ Initialise a virtual environment named .venv
python -m venv .venv
# 3️⃣ Activate it (Linux/macOS)
source .venv/bin/activate
# 4️⃣ Activate it (Windows PowerShell)
# .venv\Scripts\Activate.ps1
# 5️⃣ Install a package with pip
pip install requests
# 6️⃣ Verify the interpreter path
which python # Linux/macOS
# or
Get-Command python # PowerShell
What venv does under the hood
- Copies the base interpreter into the folder (
.venv/bin/python). - Creates an empty
site-packagesdirectory forpipto fill. - Writes a small
activatescript that prepends the environment’sbin(orScripts) folder toPATH.
Limitations
- No built‑in package solver; you rely on
pip’s simple dependency resolver. - No support for non‑Python binaries (e.g.,
conda’s compiled libraries). - No native lock‑file generation (you must create
requirements.txtmanually).
Part 3 – conda – the all‑in‑one data‑science manager
When to choose conda
- Your project needs compiled libraries (e.g.,
numpy,pandas,scipy) that are tricky to build from source. - You want to manage multiple Python versions and non‑Python dependencies (e.g.,
libsqlite,ffmpeg). - You work in a data‑science or machine‑learning environment where the Anaconda/Miniconda distribution is already standard.
Install Miniconda (lightweight)
# Linux/macOS – download installer script
curl -fsSL https://repo.anaconda.com/miniconda/Miniconda3-latest-Linux-x86_64.sh -o miniconda.sh
bash miniconda.sh -b -p $HOME/miniconda
# Add to PATH for the current session
export PATH="$HOME/miniconda/bin:$PATH"
(Windows users can download the .exe installer from the same URL.)
Create and activate a conda environment
# 1️⃣ Create an environment named "myconda" with Python 3.11
conda create -n myconda python=3.11 -y
# 2️⃣ Activate it
conda activate myconda
# 3️⃣ Install a mix of Python and non‑Python packages
conda install numpy pandas -y # pulls compiled binaries from conda‑forge
pip install fastapi # pip works inside a conda env, too
# 4️⃣ Export a reproducible lock file
conda env export > environment.yml
What conda adds
| Feature | conda provides |
|---|---|
| Cross‑platform binaries | Packages compiled for Windows, macOS, Linux in a single channel. |
| Channel system | Official defaults and community‑run conda-forge let you pick the most up‑to‑date builds. |
| Environment export | environment.yml captures Python version, channel URLs, and exact package builds. |
| Solver | A SAT‑based dependency solver that can resolve complex version constraints quickly. |
Drawbacks
- The base installation (Miniconda/Anaconda) is ~400 MB, which may be overkill for tiny scripts.
- Environments can become large because each one often includes its own copy of the Python interpreter and many compiled libs.
Part 4 – uv – the ultra‑fast, modern alternative
When to choose uv
- You love speed:
uvclaims to be 10–100× faster thanpipfor installing wheels and creating environments. - Your workflow is pure‑Python (no need for heavy compiled libs).
- You want a single binary that works on Windows, macOS, and Linux without a separate installer.
Install uv
# macOS / Linux – one‑liner
curl -LsSf https://astral.sh/uv/install.sh | sh
# Windows PowerShell
irm https://astral.sh/uv/install.ps1 | iex
The script drops uv into ~/.local/bin (Linux/macOS) or %USERPROFILE%\.uv\bin (Windows) and adds it to PATH.
Create a project with uv
# 1️⃣ Initialise a new project folder
mkdir my_uv_project && cd my_uv_project
uv init # creates pyproject.toml and a basic src layout
# 2️⃣ Create a virtual environment (uv does it automatically on first install)
uv venv .venv # optional: specify a location, otherwise .venv is default
# 3️⃣ Activate the env (same as venv)
source .venv/bin/activate # Linux/macOS
# .venv\Scripts\Activate.ps1 # Windows PowerShell
# 4️⃣ Install packages – uv uses its own fast resolver
uv pip install httpx==0.27.0
# 5️⃣ Generate a lock file
uv lock
What makes uv special
| Feature | Description |
|---|---|
| Rust‑based resolver | Compiled in Rust, giving sub‑second dependency solving even for large graphs. |
| Parallel wheel building | Downloads and builds wheels concurrently, shaving minutes off large installs. |
| PEP 517/518 compliance | Reads pyproject.toml for build requirements, so you can define build‑system metadata once. |
| Zero‑runtime dependencies | A single executable; no Python interpreter required for the installer itself. |
Caveats
- Still relatively new (first stable release in 2023); some obscure packages may not yet have wheels that
uvcan handle. - Doesn’t manage non‑Python binaries; you’ll need
condaor system packages for those.
Hands‑on example – A tiny Flask‑like web service
We’ll build a minimal HTTP server that fetches a JSON placeholder and prints the title. The code works with any of the three env managers; we’ll show the venv workflow, then note the equivalent conda/uv commands.
Project layout
my_demo/
├─ app.py
├─ requirements.txt # for venv & pip
└─ environment.yml # for conda (optional)
Step‑by‑step
# 1️⃣ Create the folder and move into it
mkdir my_demo && cd my_demo
# 2️⃣ Write the script (copy‑paste into app.py)
cat > app.py <<'PY'
import httpx
def main():
resp = httpx.get("https://jsonplaceholder.typicode.com/todos/1")
resp.raise_for_status()
data = resp.json()
print(f"Title: {data['title']}")
if __name__ == "__main__":
main()
PY
Using venv
# Create and activate a venv
python -m venv .venv
source .venv/bin/activate # Windows: .venv\Scripts\activate
# Pin the exact version we need
pip install "httpx==0.27.0"
# Freeze the environment (optional but helpful)
pip freeze > requirements.txt
# Run the script
python app.py
Using conda
conda create -n demo python=3.11 -y
conda activate demo
conda install -c conda-forge httpx -y # pulls pre‑built binary
conda env export > environment.yml
python app.py
Using uv
uv venv .venv
source .venv/bin/activate
uv pip install "httpx==0.27.0"
uv lock # creates uv.lock
python app.py
Expected output
Title: delectus aut autem
If you see that line, you’ve successfully isolated a Python interpreter, installed a third‑party library, and run code inside the environment—exactly what a virtual environment is meant to guarantee.
Common mistakes & troubleshooting
| Symptom | Likely cause | Fix |
|---|---|---|
command not found: python after activation |
Wrong activation script (e.g., used Windows activate on macOS) |
Run the correct script for your OS (source .venv/bin/activate on *nix, .venv\Scripts\Activate.ps1 on Windows PowerShell). |
ImportError: No module named httpx |
Package installed in a different environment | Ensure the environment is active (which python should point inside .venv). Re‑install with pip install httpx. |
CondaValueError: prefix already exists |
Trying to create a conda env that already exists | Either delete the old env (conda env remove -n demo) or reuse it (conda activate demo). |
uv: error: could not find a version that satisfies the requirement … |
Package has no pre‑built wheel for your platform | Fall back to pip inside the uv env (uv pip install package_name) or use conda for compiled libs. |
Environment activation works, but python --version shows system Python |
Activation script modifies PATH incorrectly (e.g., missing export PATH=...) |
Re‑source the activation script or open a fresh terminal; avoid modifying PATH manually before activation. |
Try it yourself
- Create a new folder called
quiz_env. - Initialise a
venv(orconda/uvif you prefer). - Install
pandas==2.2.0andmatplotlibinside the env. - Write a one‑line script that prints the first five rows of
pandas.DataFrame({"a":[1,2,3]}). - Run the script while the env is active and verify the output.
If you hit any of the errors above, apply the corresponding fix.
What’s next
- Dependency lock files deep dive – how
requirements.txt,environment.yml, anduv.lockdiffer and when to use each. - Cross‑platform CI pipelines – setting up GitHub Actions to test your project in
venv,conda, anduvautomatically. - Mixing conda and pip – best practices for installing pure‑Python wheels on top of a conda base.
- Performance benchmarking – real‑world timing of
pip,conda, anduvon a 100‑package data‑science stack.
Bookmark this guide for quick reference when you set up your next Python project.