刚接触 Linux 时,我面临的最大障碍不是命令记不住,而是“一台 Windows 电脑怎样才能舒服地跑 Linux”。双系统要重启切换,虚拟机又觉得笨重。直到用上 WSL(Windows Subsystem for Linux),这个问题才算真正解决:不需要另装系统,Windows 自带内核级支持,直接命令行进入 Ubuntu、Debian 环境,文件和 Windows 互通。配合 PowerShell、CMD、Windows Terminal 这些终端工具,以及 apt 这个包管理器,日常学习和实践完全够了。这集就把这一套环境从零讲清楚,重点是 WSL 安装、终端选择、apt 命令,以及新手最容易懵的 Package Dependency(软件包依赖)到底是怎么运作的。
这集适合谁?想学 Linux 但只有 Windows 机器的零基础朋友;需要在 Windows 上跑开源工具又不想开虚拟机的开发者;还有刚接触服务器运维、想先在本地练手的人。读完你可以自己搭好一个能敲 Linux 命令、能装软件、能排查依赖问题的开发环境。
1. 项目概述:为什么我建议从 WSL 而不是虚拟机开始学 Linux
1.1 双系统、虚拟机、WSL 三种方案怎么选
我见过不少人为了学 Linux 直接把自己的 Windows 换成 Linux 桌面,结果打印机不认、网银装不上、文档排版错乱,折腾一星期又换回去。这不是意志力问题,是工具选错了。对绝大多数学习者来说,目标不是“让电脑跑 Linux”,而是“能用 Linux 环境学习和干活”,这两件事差别很大。
双系统的痛点很明显:切换要重启,磁盘分区紧张,而且 Windows 和 Linux 之间的文件互访非常别扭。虚拟机(VMware、VirtualBox)稍微好一点,可以边用 Windows 边开一个 Linux 窗口,但内存开销大,启动要几分钟,共享文件夹、剪贴板、网络的配置也经常让人头大。WSL 2 的出现改变了这个局面:它底层是微软帮你托管的一个轻量虚拟机,但和 Windows 的集成度极高,终端里直接输入wsl就能进去,文件系统可以互访,剪贴板通用,启动速度接近秒级。
当然,WSL 也不是万能的。它不适合跑需要特定内核模块的场景,不适合做硬实时任务,也不适合当生产服务器。但用于学习 Linux 基础、跑 Python 脚本、装开发环境、写 Shell 脚本,完全够用。
1.2 WSL 1 和 WSL 2 到底差在哪
WSL 经历过两代架构。WSL 1 走的是“系统调用翻译层”路线:把 Linux 程序发出的系统调用直接翻译成 Windows 的系统调用,启动速度和文件性能不错,但对内核的兼容性有限,有些软件跑不起来。WSL 2 则换成了真正的轻量虚拟机,内置一个完整 Linux 内核,兼容性大大提升,Docker、CUDA 这类对内核有要求的场景也能正常使用。代价是会吃掉一些内存,并且会有一个虚拟磁盘文件存在 Windows 盘上。
检查当前用的是哪个版本,在 PowerShell 里运行:
wsl -l -v如果看到VERSION列是 2,那已经很理想。如果是 1,可以单独把某个发行版切换成 2:
wsl --set-version Ubuntu-22.04 2提示:新版 Windows 10/11 执行
wsl --install默认安装的已经是 WSL 2,不需要额外处理。如果你的系统因为组策略或老版本原因装出来还是 WSL 1,再用上面命令升上去。
2. 终端三件套:CMD、PowerShell 与 Windows Terminal 的分工
2.1 三个终端到底是什么关系
很多新手被三个“黑窗口”搞糊涂:CMD、PowerShell 和 Windows Terminal 长得差不多,到底用哪个?我的理解很简单:
- CMD是 Windows 的元老级命令提示符,起源于 DOS 和早期批处理。它能做的事情有限,主要用来启动程序、操作文件、运行简单的批处理脚本。
- PowerShell是微软后来推出的“加强版 shell”,它面向对象,管道里传递的不只是文本,而是结构化的对象。比如
Get-Process列出进程后,可以直接接Where-Object做筛选,比在 CMD 里用 findstr 处理文本方便得多。 - Windows Terminal则不是命令解释器,它是一个“外壳”,一个现代终端模拟器。它可以同时开多个标签页,每个标签页可以跑 CMD、PowerShell、WSL 或者 Git Bash,支持多主题和 GPU 渲染。打个比方:CMD 和 PowerShell 是司机,Windows Terminal 是同一台车。
对日常使用来说,不用非得学会 PowerShell 的复杂语法,只需要知道在这三个环境里怎么调用 WSL 就够了。热词里经常出现的“在 PowerShell 中运行 wsl --status”就是指在 Windows 的任一终端里执行 WSL 相关命令。
2.2 从 Windows 终端进入 WSL 的几种方式
进入 WSL 最直接的方式是开始菜单里找到安装好的发行版图标(比如 Ubuntu),点击后会打开一个窗口直接进入 Linux shell。不过我更推荐在 PowerShell 或 Windows Terminal 里操作,因为这样能同时管理 Windows 命令和 Linux 命令。
打开 PowerShell,输入:
wsl就会自动进入默认发行版的 Linux shell,提示符会变成用户名@主机名:~$。如果想进入某个特定发行版(比如你同时装了 Ubuntu 和 Debian),用:
wsl -d Debian需要退出 WSL 时,输入exit,就会回到 Windows 的终端环境。
在 Windows Terminal 里,点标题栏的“向下箭头”会看到“新建配置文件”列表,选择对应的发行版即可。如果装了 WSL 发行版,它通常会自动出现在列表里。日常我用 Windows Terminal 的频率最高,因为多标签页太方便了:一个标签折腾 Linux,一个标签跑 PowerShell,互不干扰。
2.3 手把手完成 WSL 安装与版本切换
这部分把整个安装流程记录下来,照着操作基本不会出错。
- 以管理员身份打开 PowerShell,运行:
wsl --install - 如果只想装某个具体发行版,可以加参数指定,比如:
wsl --install -d Ubuntu-22.04 - 安装完成后,重启电脑。重启后首次进入会在终端里弹出一个启动画面,让你设置 Linux 用户的用户名和密码。
- 设置完成后,进入 Linux shell,验证一下版本:
cat /etc/os-release - 回到 Windows PowerShell,用
wsl -l -v查看是否显示 VERSION 为 2。
有一点值得提醒:wsl --install依赖 Windows 的“虚拟机平台”功能,如果执行时报错提示需要启用虚拟化,需要去 BIOS 里确认 Intel VT-x 或 AMD SVM 是否开启。
3. 核心命令:apt 到底帮你做了什么
3.1 apt update 与 apt upgrade:先刷新货架,再更新商品
在 Linux 里安装软件,最常用的是 apt 命令。它全称 Advanced Package Tool,是 Debian/Ubuntu 系的软件包管理器。很多人第一次接触apt update时会疑惑:我还没装软件,为什么先要执行一个 update?这里的update并不是升级系统,而是“更新软件源索引”,也就是让本机知道远程软件仓库里有哪些软件、当前版本是多少。
打个比方:apt update相当于去超市前先刷新一遍购物清单,apt upgrade才是把清单上已经买过的商品替换成更新版本。如果跳过 update,本地的索引可能是陈旧的,apt install会发现找不到软件包或者装到老版本。
实际操作中我会在每次安装软件之前先执行:
sudo apt update然后根据需要再决定要不要 upgrade:
sudo apt upgrade注意:
apt upgrade会一次性更新很多软件包,在服务器或正在运行的开发环境上执行前,最好看一眼输出里“将被升级”的列表。WSL 里一般问题不大,但如果跑着生产环境,不建议盲目升级所有包。
3.2 安装、卸载、清理:apt 的日常动作
常用命令的语义有必要厘清,不然容易在卸载时误删数据:
sudo apt install <package> sudo apt remove <package> sudo apt purge <package> sudo apt autoremove sudo apt cleanremove只是卸载软件本身,配置文件一般保留;purge则连配置文件一起删,适合彻底清理某个软件。autoremove用来清理那些“因为安装某软件而被顺带装进来、但现在没用了”的依赖包。比如你把某个大软件卸载后,它的一些依赖残留下来,就可以用 autoremove 清掉。
实际中的常见操作组合是:
sudo apt install git curl vim一次安装多个包,每个包名之间用空格隔开,apt 会统一处理它们的依赖。
3.3 Package Dependency 到底是什么,为什么它决定着安装体验
Package Dependency(软件包依赖)是 Linux 新手最容易迷糊的概念之一。Windows 上安装软件,一般双击 exe 或 msi,安装器已经把你需要的运行库打进去了。Linux 不是这样:一个软件包通常只包含自己的可执行文件、配置文件和文档,而它运行时依赖的动态链接库或其他程序,往往属于另外的软件包。
举个例子,你安装git时,apt 会提示“以下软件包将被额外安装”,这些额外包里面就有libcurl4、libexpat1之类的运行库。Git 是一个用 C 写的程序,它运行的第一步就是去系统目录里找到这些动态库(.so文件)并加载。如果缺少某个库,程序就会报error while loading shared libraries。
可以用下面命令直观地看:
ldd /usr/bin/git输出里每一行就是一个依赖的动态库。再看软件包层面的依赖关系:
apt-cache depends git这个命令会列出 git 依赖的包,包括Depends(强依赖)和Suggests(建议安装的增强功能)。
反过来,可以用apt-cache rdepends git看哪些包依赖 git。这样你就能理解依赖树的概念:软件包之间形成一个层级网络,A 依赖 B,B 依赖 C。apt 的价值就在于,它替你把这棵依赖树理顺了,安装 A 时自动把 B、C 全装上,卸载时也能判断哪些包变成孤儿依赖。
对用户来说,最直观的感受是:在 Linux 上装软件基本不用担心“这个程序缺个 DLL 去哪找”,apt 会一次性处理好。这也是现代包管理器最重要的价值之一。
3.4 本地 .deb 包:为什么也建议用 apt install
热词里有一个很典型的场景:
cd ~/downloads sudo apt install ./spark-store*.deb这里./加软件包路径,是让 apt 从一个本地.deb文件安装,而不是从远程仓库下载。为什么要强调用apt install ./xxx.deb而不是dpkg -i xxx.deb?因为dpkg -i只知道“把这个包装上”,它不会自动去仓库里下载这个包缺失的依赖;如果缺依赖,就会报一堆dependency is not satisfiable的错误,你得手动apt install -f修复。而apt install ./xxx.deb会自动解析该软件包的依赖并补装,省掉不少麻烦。
shell 里的通配符*.deb也有讲究:在 bash 中,./spark-store*.deb会被自动展开成当前目录下所有匹配的.deb文件。这个技巧在你手动下载了多个软件包时特别有用。
4. 实操过程:从零配置一个能写代码的 WSL 环境
4.1 更换软件源:解决下载慢的第一步
国内访问 Ubuntu 默认源经常很慢,换源是我每次装完 WSL 后的第一件事。思路很简单:把/etc/apt/sources.list里的默认服务器地址,换成国内镜像站地址。以 Ubuntu 22.04 为例:
先备份原文件:
sudo cp /etc/apt/sources.list /etc/apt/sources.list.bak然后用你熟悉的编辑器修改:
sudo nano /etc/apt/sources.list注释掉原来的archive.ubuntu.com相关行,换成以下内容(这里是清华源的示例):
deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy main restricted universe multiverse deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-updates main restricted universe multiverse deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-backports main restricted universe multiverse deb https://mirrors.tuna.tsinghua.edu.cn/ubuntu/ jammy-security main restricted universe multiverse保存后执行:
sudo apt update如果输出里Get行的速度明显加快,说明换源成功。
提示:不同 Ubuntu 版本(比如 22.04 的代号是 jammy,24.04 的代号是 noble)对应源地址不同,别照着老文章硬抄。可以先执行
lsb_release -a查看代号。
4.2 用 apt 批量安装常用开发工具
先来一套最常用的组合:
sudo apt install build-essential git curl wget vim python3 python3-pip各工具的用途不展开说,单挑几个容易踩坑的点:
build-essential包含 gcc、make 等编译工具,之后如果自己编译源码,这是必备组件。python3和python3-pip是分开装的,不要以为装了 python3 就自带 pip。有些系统里 pip 命令会指向 pip3,使用时注意。vim默认是 vim-tiny 还是完整版,取决于源配置,vim --version可查看。
热词里还有一句sudo apt install jmeter。JMeter 这种工具在 Ubuntu 仓库里可能没有,或版本比较旧。如果apt search jmeter找不到,可以去 Apache 官网下载 tar 包,放到~/tools里解压直接用。这正好印证了包管理器的边界:apt 能解决很多问题,但不是所有软件的官方发布渠道都走 apt。
安装时如果遇到E: Unable to locate package,一般就是没执行sudo apt update导致索引里没有这个包。这也是新手第一反应应该检查的事。
4.3 让 VS Code 和 WSL 无缝协作
热词里“在 vscode 中使用 wsl”我强烈推荐。步骤非常简单:在 Windows 侧安装 VS Code,然后在扩展市场搜索装Remote - WSL插件。回到 WSL 终端,进入你的项目目录,直接输入:
code .VS Code 会自动以“WSL 模式”启动,左下角会出现绿色的WSL: Ubuntu-...标识。这时候编辑文件、运行终端、调试代码,全部是在 WSL 环境里完成的。
这里有个性能小技巧值得专门写一句:代码文件一定要放在 Linux 文件系统里,比如~/projects,而不是放在C:\Users\你\projects(WSL 里对应路径是/mnt/c/Users/你/projects)。因为 WSL 访问 Windows 盘文件走的是跨文件系统协议,IO 性能会差很多,尤其是跑依赖大量小文件的构建任务时,差距非常明显。
5. 常见问题与避坑实录
5.1 “用户不在 sudoers 文件中”怎么救
很多人在 WSL 里执行sudo apt update时遇到过这样的输出:
[sudo] 你的用户名 的密码: 你的用户名 未出现在 sudoers 文件中。此事将被报告。出现这个报错,说明当前用户没有被加入sudo组,无法提权。解决方法不复杂:回到 Windows PowerShell,以 root 身份进入发行版(不需要密码):
wsl -u root然后在 Linux 里把用户加进 sudo 组:
usermod -aG sudo 你的用户名Debian 系也可能是:
adduser 你的用户名 sudo退出重新进入终端,问题就解决了。
这里强调一点:不要图省事直接编辑/etc/sudoers文件,特别是不要用一个错误的语法把文件写坏。改 sudoers 的正确姿势是用visudo命令,它会在保存前检查语法错误。我见过新手手工改了 sudoers 导致整个系统无法提权,只能靠wsl -u root进去修复,这其实很麻烦。
5.2 apt 锁冲突:另一个程序正在运行
安装软件时偶尔会遇到:
Could not get lock /var/lib/dpkg/lock-frontend这提示你上游的dpkg(apt 的底层工具)正被另一个进程占用。常见原因是后台的自动更新任务还在运行,或者之前一次安装中断了,进程还挂着。可以用命令看看是哪个进程:
ps aux | grep -E 'apt|dpkg'发现可疑进程后,等它结束,或者确认无误后结束它:
sudo kill -9 <进程号>网上很多教程会直接让你删/var/lib/dpkg/lock文件,我的经验是:除非确认没有任何 apt/dpkg 进程在跑,否则不要删锁文件。锁文件在,最多让你等;锁文件没了且进程还活着,才真正可能把 dpkg 数据库写坏。
5.3 WSL 空间占满 C 盘,迁移到 D 盘
WSL 2 的数据存在一个叫ext4.vhdx的虚拟磁盘文件里,默认位置在 C 盘用户的AppData\Local\Packages下面。用一段时间后,这个文件能涨到十几个 GB,C 盘吃紧是必然的。
迁移步骤记录一下,亲测可用:
- 先关闭 WSL:
wsl --shutdown - 导出发行版到目标盘:
wsl --export Ubuntu-22.04 D:\wsl\ubuntu.tar - 注销原发行版(注意:这步会删掉原注册信息,但不会删导出的 tar 文件):
wsl --unregister Ubuntu-22.04 - 导入到新路径:
wsl --import Ubuntu-22.04 D:\wsl\ubuntu D:\wsl\ubuntu.tar
导入后默认登录用户会变成 root,需要重新设置默认用户。编辑一下/etc/wsl.conf:
[user] default=你的用户名然后wsl --shutdown再重新打开即可。
提示:导出前一定要先
wsl --shutdown,否则虚拟磁盘可能处于不完整状态,导出的 tar 文件在后面导入时可能报错。
5.4 网络不通、DNS 解析慢怎么办
WSL 里偶尔会遇到curl某个网址没反应,但 Windows 上访问同样的网址却正常。我先排查的是 DNS:
cat /etc/resolv.conf如果看到 nameserver 是异常的地址(比如自动生成的 NAT 网关地址解析不出来),可以试试换个公共 DNS,修改/etc/resolv.conf后,为了防止被 WSL 自动重置,还需要在/etc/wsl.conf里写:
[network] generateResolvConf = false然后执行:
sudo rm /etc/resolv.conf sudo nano /etc/resolv.conf写入公共 DNS 地址保存。这种方式在 WSL 网络模式下是有效的。如果你只是下载软件包很慢,前面 4.1 已经说过,换镜像源是最优解。
5.5 排查问题速查表
把上面几个问题整理成一张表,方便你快速定位:
| 现象 | 可能原因 | 首选解法 |
|---|---|---|
user is not in the sudoers file | 用户不在 sudo 组 | wsl -u root加用户入 sudo 组 |
Could not get lock /var/lib/dpkg/lock-frontend | apt/dpkg 进程占用 | ps aux查进程,等待或结束进程 |
E: Unable to locate package | 软件源索引未更新 | 先执行sudo apt update |
error while loading shared libraries | 缺少动态库依赖 | 用apt install -f或补装对应库包 |
wsl -l -v显示 VERSION 为 1 | 未切换到 WSL 2 | wsl --set-version <发行版> 2 |
| C 盘空间骤减 | ext4.vhdx 文件膨胀 | 按 5.3 方法迁移到其他盘 |
5.6 记不住命令不用慌:用工具代替死记硬背
最后分享一个心态上的技巧。Linux 命令多到没人能全记下来,我不建议背命令表。遇到不知道用法的情况,先看命令自带的帮助:
命令 --help想查某个命令的详细说明,用man:
man apt想找“某个功能该用哪个命令”,有apropos。比如你忘了“复制”相关的命令有哪些:
apropos copy这比翻收藏的文章高效得多。同时,建议在 WSL 里自己建一个笔记文件,比如~/notes/linux-commands.md,把每次踩坑的解法记下来。这个习惯帮你积累起来,比任何教程都贴合你自己的工作场景。
这集我们从 WSL 的环境搭建讲到终端选择,再到 apt 命令和依赖关系的底层逻辑,最后聊了不少坑。我在实际使用中的一个体会是:理解“软件包依赖”这套思想比记住几个 apt 参数重要得多,它不仅是 apt 的运作核心,也是之后接触 Docker 镜像、Conda 环境、Ansible 自动化时的通用基础。装完环境,没事多敲几条命令,看看ldd的输出,翻了apt-cache depends的结果,你对 Linux 的掌控感会慢慢建立起来。下一集,可以聊聊文件系统、权限模型和 Shell 脚本,有环境在手里,学什么都会更快。