Skip to content

Linux 单次执行多个命令

zzh0u

每天都在和 Linux 打交道,那么 Shell 基本就是最高频的工具之一。无论是处理文件、安装软件,还是写一些顺手的小脚本,很多操作都离不开命令行。而在日常使用中,一个很常见的需求就是把多条命令串起来执行。这样可以少敲几次回车,也能把连续操作写得更紧凑一些。

Shell 里最常见的三种命令连接方式是 ;&&||。它们看起来只是几个简单符号,但执行逻辑并不一样。真正理解这三者的区别,能少踩很多坑。

;:前后命令都会执行

语法很简单:

cmd1 ; cmd2

它的含义是:不管 cmd1 成功还是失败,cmd2 都会继续执行。

例如:

whoami; cat zzh0u.md; date

这条命令会按顺序做三件事:

即使 cat zzh0u.md 失败了,最后的 date 还是会继续执行。

所以,; 更适合那些彼此独立的命令。比如前一条命令失败了,也不影响后一条命令继续跑。不过它也是最容易埋坑的一种写法。因为 Shell 不会帮你判断前一步是不是成功了。比如下面这条命令:

cd .. ; rm -rf *

如果 cd .. 写错了(oh-my-zsh 或某些终端主题支持用 cd ... 替代 cd ../..),或者目录根本不存在,后面的 rm -rf * 仍然会执行。这种情况下,删掉的就未必是你想删的东西了。

&&:前一条成功,后一条才执行

语法如下:

cmd1 && cmd2

&& 可以理解为逻辑与。只有当 cmd1 执行成功,cmd2 才会继续执行。例如:

mkdir demo && cd demo && touch main.go

这条命令的执行逻辑是:

只要中间任意一步失败,后续命令都会停止。

这也是我更推荐日常优先使用的连接方式,尤其是在“后一条命令依赖前一条命令结果”的场景里。相比 ;&& 的安全性会高很多。还是上面的例子,如果改成:

cd .. && rm -rf *

那么只有在成功切换到目标目录之后,删除命令才会执行。这个习惯在处理文件、跑部署脚本、批量改目录时都很重要。

||:前一条失败,后一条才执行

语法如下:

cmd1 || cmd2

|| 可以理解为逻辑或。只有当 cmd1 执行失败时,cmd2 才会执行。它常用于“失败后的兜底逻辑”。

例如:

find zzh0u.md || touch zzh0u.md

这条命令的含义是:

这里顺手提一句,touch 在文件已存在时通常也会执行成功,它更多是更新时间戳,而不是仅在文件不存在时创建。

|| 的另一个常见用途是提供降级方案,例如:

command -v brew >/dev/null 2>&1 || echo "brew is not installed"

如果系统里没有 brew,就输出一条提示信息。

什么时候该用哪一个?

可以简单记成下面三条:

如果只是图省事把所有命令都用 ; 串起来,短期看起来方便,长期往往更容易出问题。尤其是涉及 cdrmmv 这类命令时,&& 往往是更稳妥的选择。

;&&|| 都能把多条命令写在一行里,但它们控制的是完全不同的执行条件。很多时候,Shell 命令写得稳不稳,不在于会不会敲命令,而在于有没有把执行条件写清楚。

Next
追龙虾的人