![bash 内置绑定和转义的问题](https://linux22.com/image/219213/bash%20%E5%86%85%E7%BD%AE%E7%BB%91%E5%AE%9A%E5%92%8C%E8%BD%AC%E4%B9%89%E7%9A%84%E9%97%AE%E9%A2%98.png)
我正在尝试将历史模糊查找热键添加到我的 bash shell 中。然而,我想要的命令被中间切断了:
[april@Capybara-2:~]$ cat ~/.bashrc
bind "\"\C-r\": \"\$(history | fzf | awk '{\$1=\"\"; print substr(\$0,2)}')\""
[april@Capybara-2:~]$ $(history | fzf | awk '{$1="";
(第二行是按下 \C+r 时的结果。)我预计 \C+r 应该绑定到$(history | fzf | awk '{$1=""; print substr($0,2)}')
,但事实并非如此。为什么?
答案1
这是引用地狱。您将命令放在双引号中,因此\"\"
变为""
,因此对于 Readline,命令如下所示:
bind "\C-r": "$(history | fzf | awk '{$1 = ""; ....
看到问题了吗?开始的字符串"$(
以 中的第一个双引号结束"";
,我不确定 Readline 的字符串连接到底是如何工作的,但似乎在结束引号后立即附加任何非空白字符,而其他所有内容都被丢弃。
我们可以使用以下任一方法相应地修复引用:
# Extra backslashes inside double quotes
bind "\"\C-r\": \"\$(history | fzf | awk '{\$1=\\\"\\\"; print substr(\$0,2)}')\""
# Wrap the macro in single quotes instead of double quotes
bind "\"\C-r\": '\$(history | fzf | awk \'{\$1=\"\"; print substr(\$0,2)}\')'"
# Use single quotes for the `bind` command argument instead of double quotes
bind '"\C-r": "$(history | fzf | awk '\''{$1=\"\"; print substr($0,2)}'\'')"'