![执行还是不执行](https://linux22.com/image/851661/%E6%89%A7%E8%A1%8C%E8%BF%98%E6%98%AF%E4%B8%8D%E6%89%A7%E8%A1%8C.png)
我正在阅读 O'Reilly 的书“Unix 简介”,我在那里看到可以使用以下格式在当前 shell 中对命令进行分组和执行:
{ cmd1 ; cmd2 }
我不明白这是怎么可能的,因为我知道对 exec 的调用会替换 shell 的数据,因此 shell 无法从 exec 系统调用返回。所以我测试了该命令,但我不明白发生了什么。我进入了一个命令行,但我不知道该命令行属于什么。
它只是从 shell 中剥离出来的终端仿真器的命令行吗?
另外,在当前 shell 中执行命令有什么用呢?
答案1
这是因为您没有终止第二行:{ cmd1; cmd2; }
是正确的。分号表示“命令结束”。
答案2
执行还是不执行
对 exec 的调用会替换 shell 的数据,因此 shell 无法从 exec 系统调用返回。
但并非每个命令都是要执行的程序的名称。因此通常不涉及exec
调用。关键区别在于,与相比( cmd1; cmd2; )
,您不会获得另一个 shell 进程。或者更准确地说,shell 只会分叉以执行子程序,而不是执行 shell 进程。
奇怪的提示
命令行属于什么。
正如其他答案所指出的那样,您的命令不完整。因此命令行属于 bash 本身,它正在等待您的组结束。
用途
另外,在当前 shell 中执行命令有什么用呢?
…与子壳层分组相反
最突出的例子是在该子命令中设置变量。这是:
foo=1; { foo=2; echo $foo; }; ( foo=3; echo $foo; ); echo $foo
这将打印
2
3
2
因此,尽管您foo=3
在一个组内进行设置,但该组是在子 shell 中执行的,其设置不会传播到父组。
另一件值得考虑的事情是当前工作目录。{ cd foo; make; }
将使您留在目录中foo
,但( cd foo; make; )
不会改变主 shell 的当前工作目录。
…与未分组的命令相反
如果你有其他外部代码,例如条件语句,那么分组非常有用
test -f foo && { echo "Foo exists."; rm foo; }
或重定向
{ echo "Content of $PWD:"; ls; } | gzip > dirlist.gz
答案3
内置help
命令甚至对于关键字也很有用{
。来自help -m {
:
NAME { ... } - Group commands as a unit. SYNOPSIS { COMMANDS ; }
;
因此,每个命令后都必须有分号 ( )。