bash:在DEBUG陷阱中保留$ _

Tom*_*ale 3 bash

bash,手册中说 $_应该是"执行的最后一个命令的最后一个参数".

这是预期的行为:

$ echo 1 2 3
1 2 3
$ echo $_
3
$ 
Run Code Online (Sandbox Code Playgroud)

使用DEBUG陷阱时,$_基于陷阱运行的最后一个命令(date在下面的示例中)而不是用户输入的最后一个命令:

$ exec bash
$ unset PROMPT_COMMAND
$ trap date DEBUG
$ echo 1 2 3
Sat Dec  3 11:54:33 ICT 2016
1 2 3
$ echo $_
Sat Dec  3 11:54:37 ICT 2016
date
$ # User blinks in confusion and says "but I didn't just type date!"
Run Code Online (Sandbox Code Playgroud)

似乎默认情况下,设置DEBUG陷阱会更改默认行为$_.

无论chruby庆典,preexec从这个苦.

有趣的是,这符合预期zsh:

$ zsh
genesis% trap date DEBUG
genesis% echo 1 2 3
Sat Dec  3 12:18:01 ICT 2016
1 2 3
genesis% echo $_
Sat Dec  3 12:18:04 ICT 2016
3
genesis%
Run Code Online (Sandbox Code Playgroud)

如何保留$_使用DEBUG陷阱时的价值?

Cha*_*ffy 6

值得注意的是"执行的最后一个命令的最后一个参数"包括文本文本"执行最后一个命令",而不是"用户输入的最后一个命令"; bash在这方面的行为就像它的文档承诺一样.

但是不要紧,除非你的陷阱永远返回非零值(因此中止它们之前运行的命令),这很容易解决:

trapfunc() { local old_=$1; date; : "$old_"; }
trap 'trapfunc "$_"' DEBUG
Run Code Online (Sandbox Code Playgroud)

  • @TomHale参数扩展和单词拆分不会发生在赋值中:`a ='hello world*.txt'; b = $ a``b`就好了. (2认同)