python 多版本管理(pyenv)
上篇文章提到了uv 可以进行 pip 包管理和 虚拟环境构建,其实,对于我们来说,还有一个需求,就是多个python环境进行管理,刚好找了下,发现了这个pyenv工具。话不多少,直接开始。
pyenv(Windows 下为pyenv-win)是Python 版本管理神器,核心解决「多 Python 版本共存、版本冲突、环境不一致」的痛点,让你在一台电脑上无痛切换不同 Python 版本,不用手动改环境变量、卸载重装,是 Python 开发的必备工具。
一、pyenv可以干什么事情?
1.1 多版本 Python 共存(最核心)
手动管理多个 Python 版本时,你需要反复修改环境变量、记住不同版本的安装路径,极易混乱;而 pyenv 能:
- 一键安装 Python 2.7/3.6/3.10/3.12 等任意版本(包括 Anaconda、Miniconda、PyPy 等衍生版本);
- 所有版本隔离存储在
~/.pyenv目录(Windows:%USERPROFILE%\.pyenv),互不干扰; - 无需卸载现有 Python,系统自带的 Python 也不会被修改 / 覆盖。
1.2. 灵活切换版本(3 种维度,按需选择)
| 切换维度 | 作用范围 | 适用场景 |
|---|---|---|
| 全局版本 | 整个系统(所有目录) | 设置系统默认 Python 版本(比如日常开发用 3.10) |
| 局部版本 | 当前目录 + 子目录 | 项目专属版本(比如给 A 项目设 3.9,B 项目设 3.11) |
| 临时版本 | 仅当前终端会话 | 临时测试某个版本(比如快速验证代码在 3.8 下是否兼容) |
1.3. 隔离不同版本的依赖包
不同 Python 版本的pip包是完全隔离的,不会出现「装了 3.10 的 Django,3.9 里也能看到」的混乱:
- 比如 Python 3.8 装
Django 4.0,Python 3.10 装Django 5.0,两者互不影响; - 解决「升级一个版本的包,导致另一个项目报错」的问题。
1. 4. 无痛安装 / 卸载 Python 版本
不用手动去 Python 官网下载安装包、手动配置路径、担心卸载残留:
- 安装:一行命令
pyenv install 3.10.11,自动下载、安装、配置; - 卸载:一行命令
pyenv uninstall 3.10.11,彻底删除该版本及对应依赖,无残留; - 安装慢?手动下载安装包到缓存目录,pyenv 会自动识别,不用改命令。
二、pyenv安装
windows系统
powershell -ExecutionPolicy Bypass -Command "Invoke-WebRequest -UseBasicParsing -Uri https://raw.githubusercontent.com/pyenv-win/pyenv-win/master/pyenv-win/install-pyenv-win.ps1 -OutFile install-pyenv-win.ps1; .\install-pyenv-win.ps1"✨ 如果你已经下载了install-pyenv-win.ps1到 Downloads 目录,直接执行:
cd C:\Users\juxuan\Downloads powershell -ExecutionPolicy Bypass -File .\install-pyenv-win.ps1✨ 脚本会自动:
- 将 pyenv-win 安装到
%USERPROFILE%\.pyenv\pyenv-win(即C:\Users\juxuan\.pyenv\pyenv-win); - 配置环境变量(
PYENV_ROOT、PATH添加bin和shims路径)。
如果你不能翻墙,脚本下载失败,我这里也有脚本内容,直接保存为install-pyenv-win.ps1。
<# .SYNOPSIS Installs pyenv-win .DESCRIPTION Installs pyenv-win to $HOME\.pyenv If pyenv-win is already installed, try to update to the latest version. .PARAMETER Uninstall Uninstall pyenv-win. Note that this uninstalls any Python versions that were installed with pyenv-win. .INPUTS None. .OUTPUTS None. .EXAMPLE PS> install-pyenv-win.ps1 .LINK Online version: https://pyenv-win.github.io/pyenv-win/ #> param ( [Switch] $Uninstall = $False ) $PyEnvDir = "${env:USERPROFILE}\.pyenv" $PyEnvWinDir = "${PyEnvDir}\pyenv-win" $BinPath = "${PyEnvWinDir}\bin" $ShimsPath = "${PyEnvWinDir}\shims" Function Remove-PyEnvVars() { $PathParts = [System.Environment]::GetEnvironmentVariable('PATH', "User") -Split ";" $NewPathParts = $PathParts.Where{ $_ -ne $BinPath }.Where{ $_ -ne $ShimsPath } $NewPath = $NewPathParts -Join ";" [System.Environment]::SetEnvironmentVariable('PATH', $NewPath, "User") [System.Environment]::SetEnvironmentVariable('PYENV', $null, "User") [System.Environment]::SetEnvironmentVariable('PYENV_ROOT', $null, "User") [System.Environment]::SetEnvironmentVariable('PYENV_HOME', $null, "User") } Function Remove-PyEnv() { Write-Host "Removing $PyEnvDir..." If (Test-Path $PyEnvDir) { Remove-Item -Path $PyEnvDir -Recurse } Write-Host "Removing environment variables..." Remove-PyEnvVars } Function Get-CurrentVersion() { $VersionFilePath = "$PyEnvDir\.version" If (Test-Path $VersionFilePath) { $CurrentVersion = Get-Content $VersionFilePath } Else { $CurrentVersion = "" } Return $CurrentVersion } Function Get-LatestVersion() { $LatestVersionFilePath = "$PyEnvDir\latest.version" (New-Object System.Net.WebClient).DownloadFile("https://raw.githubusercontent.com/pyenv-win/pyenv-win/master/.version", $LatestVersionFilePath) $LatestVersion = Get-Content $LatestVersionFilePath Remove-Item -Path $LatestVersionFilePath Return $LatestVersion } Function Main() { If ($Uninstall) { Remove-PyEnv If ($? -eq $True) { Write-Host "pyenv-win successfully uninstalled." } Else { Write-Host "Uninstallation failed." } exit } $BackupDir = "${env:Temp}/pyenv-win-backup" $CurrentVersion = Get-CurrentVersion If ($CurrentVersion) { Write-Host "pyenv-win $CurrentVersion installed." $LatestVersion = Get-LatestVersion If ($CurrentVersion -eq $LatestVersion) { Write-Host "No updates available." exit } Else { Write-Host "New version available: $LatestVersion. Updating..." Write-Host "Backing up existing Python installations..." $FoldersToBackup = "install_cache", "versions", "shims" ForEach ($Dir in $FoldersToBackup) { If (-not (Test-Path $BackupDir)) { New-Item -ItemType Directory -Path $BackupDir } Move-Item -Path "${PyEnvWinDir}/${Dir}" -Destination $BackupDir } Write-Host "Removing $PyEnvDir..." Remove-Item -Path $PyEnvDir -Recurse } } New-Item -Path $PyEnvDir -ItemType Directory $DownloadPath = "$PyEnvDir\pyenv-win.zip" (New-Object System.Net.WebClient).DownloadFile("https://github.com/pyenv-win/pyenv-win/archive/master.zip", $DownloadPath) Start-Process -FilePath "powershell.exe" -ArgumentList @( "-NoProfile", "-Command `"Microsoft.PowerShell.Archive\Expand-Archive -Path \`"$DownloadPath\`" -DestinationPath \`"$PyEnvDir\`"`"" ) -NoNewWindow -Wait Move-Item -Path "$PyEnvDir\pyenv-win-master\*" -Destination "$PyEnvDir" Remove-Item -Path "$PyEnvDir\pyenv-win-master" -Recurse Remove-Item -Path $DownloadPath # Update env vars [System.Environment]::SetEnvironmentVariable('PYENV', "${PyEnvWinDir}\", "User") [System.Environment]::SetEnvironmentVariable('PYENV_ROOT', "${PyEnvWinDir}\", "User") [System.Environment]::SetEnvironmentVariable('PYENV_HOME', "${PyEnvWinDir}\", "User") $PathParts = [System.Environment]::GetEnvironmentVariable('PATH', "User") -Split ";" # Remove existing paths, so we don't add duplicates $NewPathParts = $PathParts.Where{ $_ -ne $BinPath }.Where{ $_ -ne $ShimsPath } $NewPathParts = ($BinPath, $ShimsPath) + $NewPathParts $NewPath = $NewPathParts -Join ";" [System.Environment]::SetEnvironmentVariable('PATH', $NewPath, "User") If (Test-Path $BackupDir) { Write-Host "Restoring Python installations..." Move-Item -Path "$BackupDir/*" -Destination $PyEnvWinDir } If ($? -eq $True) { Write-Host "pyenv-win is successfully installed. You may need to close and reopen your terminal before using it." } Else { Write-Host "pyenv-win was not installed successfully. If this issue persists, please open a ticket: https://github.com/pyenv-win/pyenv-win/issues." } } Main 三、pyenv使用方法
1. 查看可安装的 Python 版本
列出所有官方可安装的 Python 版本(含 3.x、2.x、anaconda 等):
pyenv install --list # 简写:pyenv install -l👉 筛选常用版本(比如只看 3.10 开头):
pyenv install -l | findstr "3.10" # Windows # pyenv install -l | grep "3.10" # Linux/macOS2. 安装指定版本的 Python
# 示例:安装Python 3.10.11 pyenv install 3.10.113. 查看已安装的 Python 版本
列出本地所有已安装的 Python 版本(*标记当前生效版本):
pyenv versions4. 切换 Python 版本(核心)
pyenv支持 3 种维度的版本切换,优先级:临时版本 > 局部版本 > 全局版本。
(1)全局版本(系统级,所有目录生效)
设置后整个系统默认使用该版本(重启终端生效):
# 示例:设置全局版本为3.10.11 pyenv global 3.10.11 (2)局部版本(目录级,仅当前目录 / 子目录生效)
针对项目目录单独设置版本(会在目录下生成.python-version文件,提交到 Git 可同步团队版本):
# 进入项目目录 cd C:\Users\juxuan\my_project # 设置局部版本为3.9.18 pyenv local 3.9.18 👉 取消局部版本:
pyenv local --unset (3)临时版本(终端会话级,仅当前终端生效)
仅在当前终端窗口生效,关闭后恢复:
# 示例:临时使用3.8.19 pyenv shell 3.8.19 👉 取消临时版本:
pyenv shell --unset5. 验证版本是否生效
设置版本后,执行以下命令确认:
# 查看Python版本(pyenv接管后的版本) python --version # 查看pip版本(对应当前Python) pip --version6. 卸载指定版本的 Python
# 示例:卸载3.8.19 pyenv uninstall 3.8.19四、其他常用命令
| 命令 | 作用 |
|---|---|
pyenv rehash | 重新生成版本映射(安装 / 卸载版本后建议执行,避免命令找不到) |
pyenv which python | 查看当前python命令的实际路径 |
pyenv root | 查看 pyenv 的安装根目录(Windows 默认:% USERPROFILE%.pyenv) |