$_ 和 !$ 有什么区别?

$_ 和 !$ 有什么区别?

我一直习惯于!$引用上一个命令的最后一个参数。

例如

~/dir » mkdir birthday
~/dir » cd !$
~/dir » cd birthday

但是我开始看到教程用来$_代替!$

我已经测试了两者,我注意到的唯一区别是微妙的,但它似乎$_会评估并执行命令,而!$会让您在点击之前检查输出,但这是和Enter之间的唯一区别吗?$_!$

更新:标记为重复项?这个问题可以通过建议问题的接受答案来回答,但这只是因为答案比所需的问题更详细。

正在寻找_$ 是什么意思?确实产生了建议的重复项,但是在询问做了什么之前我已经知道了!$,并且没有任何迹象表明该问题也可以回答其他问题。

答案1

运行man bash并搜索部分特殊参数。因为_你会发现:

扩展到上一个命令的最后一个参数,扩展后

稍微详细一点的版本可能是......

扩展为上一个命令收到的最后一个参数,即在执行 Shell 扩展之后

我认为几个例子会真正有帮助,而不是进一步解释。

实施例1

$ echo "$(date +%s)" # %s is seconds since epoch
1536984661
$ echo $_ !$ "$(date +%s)" # don't hit enter until a few seconds pass
1536984661 1536984665 1536984665

$_获取传递给前面的实际值echo,因此它解析为过去的秒数纪元值。同时,since!$被简单地替换为打字的最后一个参数的值,即"$(date +%s)",它解析为与其后面的参数相同的较晚时间。

实施例2

$ foo='a b c'
$ echo "$foo"  # expands to single arg: 'a b c'
a b c
$ echo "$_"
a b c
$ #---------
$ echo $foo    # expands to three args: a b c
a b c
$ echo "$_"
c

请注意,第二次$foo被回应时没有被引用。因此,在传递给echo它之前,要经历变量/参数扩展和分词。这种扩张/分裂导致A,C作为三个单独的参数传递给echo并因为$_仅分配了我们仅看到的最后一个参数C。 (如果!$使用ABC仍然会显示,因为它只是被您输入的值替换,即$foo。)

$_除了上述内容之外, vs还有更多的实用价值,!$因为前者是一个变量。因此,例如,如果最后一个参数是,/some/file/path.txt您可以获取它的长度${#_} -> 19、仅提取文件名${_##*/} -> path.txt、更改根目录${_//some/other} -> /other/file/path.txt等等。不能用 做任何事!$


最后,请注意$_在其他上下文中具有不同的含义:

在 shell 启动时,设置为用于调用在环境或参数列表中传递的 shell 或正在执行的 shell 脚本的绝对路径名。

...和...

还设置为用于调用执行的每个命令并放置在导出到该命令的环境中的完整路径名。

...和...

检查邮件时,该参数保存当前正在检查的邮件文件的名称。

相关内容