当然,有一种超级简单的智能方法可以执行此操作,但是由于zshell中的历史记录似乎是fc的别名,因此无法使用如何从历史记录中删除单行中提到的技巧。。
关于如何执行此操作的任何指示?我的用例是从历史记录中删除最后一个发出的命令,以使其停止自动完成(通常是在您输错了某些内容并不断显示时)。
我知道我可以通过执行以下操作获得最后发出的命令
history | tail -n 1
,但历史记录-d无效,并且我找不到有关zsh的适当文档。
当然,有一种超级简单的智能方法可以执行此操作,但是由于zshell中的历史记录似乎是fc的别名,因此无法使用如何从历史记录中删除单行中提到的技巧。。
关于如何执行此操作的任何指示?我的用例是从历史记录中删除最后一个发出的命令,以使其停止自动完成(通常是在您输错了某些内容并不断显示时)。
我知道我可以通过执行以下操作获得最后发出的命令
history | tail -n 1
,但历史记录-d无效,并且我找不到有关zsh的适当文档。
Answers:
Zsh没有提供真实的历史记录版本功能。命令历史记录基本上是只读的。您所能做的就是批发替换它。
要编辑命令行历史记录:
fc -W
fc -R
您可以通过设置选择文件名HISTFILE
。
未经测试的代码:
remove_last_history_entry () {
setopt local_options extended_history no_hist_save_no_dups err_return
local HISTFILE=~/.zsh_history_tmp_$$ SAVEHIST=$HISTSIZE
fc -W
ed -s $HISTFILE <<EOF >/dev/null
d
w
q
EOF
fc -R
}
是的,这是一个古老的话题,但是这些问题都没有为我回答,所以我也花了很长时间尝试解决这个问题!
这是我的解决方案,感谢@Gilles对使用'fc -R'和'fc -W'的提示:)。
将下面的脚本粘贴到您的.zshrc文件中。
用源.zshrc重新加载
然后键入“忘记”以忘记最后一条命令:D。输入“忘记3”以忘记最后3个命令。一些性感的嘘声。
按下向上箭头将直接带您到最后一个命令,也不会记住单词“ forget” :)。
更新:添加了主路径,因此它现在可以在所有目录中使用。
更新2:添加了传递您想忘记的最后命令数量的功能:D。尝试“忘记2”以忘记最后2个命令:D。
# Put a space at the start of a command to make sure it doesn't get added to the history.
setopt histignorespace
alias forget=' my_remove_last_history_entry' # Added a space in 'my_remove_last_history_entry' so that zsh forgets the 'forget' command :).
# ZSH's history is different from bash,
# so here's my fucntion to remove
# the last item from history.
my_remove_last_history_entry() {
# This sub-function checks if the argument passed is a number.
# Thanks to @yabt on stackoverflow for this :).
is_int() ( return $(test "$@" -eq "$@" > /dev/null 2>&1); )
# Set history file's location
history_file="${HOME}/.zsh_history"
history_temp_file="${history_file}.tmp"
line_cout=$(wc -l $history_file)
# Check if the user passed a number,
# so we can delete x lines from history.
lines_to_remove=1
if [ $# -eq 0 ]; then
# No arguments supplied, so set to one.
lines_to_remove=1
else
# An argument passed. Check if it's a number.
if $(is_int "${1}"); then
lines_to_remove="$1"
else
echo "Unknown argument passed. Exiting..."
return
fi
fi
# Make the number negative, since head -n needs to be negative.
lines_to_remove="-${lines_to_remove}"
fc -W # write current shell's history to the history file.
# Get the files contents minus the last entry(head -n -1 does that)
#cat $history_file | head -n -1 &> $history_temp_file
cat $history_file | head -n "${lines_to_remove}" &> $history_temp_file
mv "$history_temp_file" "$history_file"
fc -R # read history file.
}
因此,这里发生了一些事情。该命令将使我们在任何命令前键入一个空格,并且不会将其添加到历史记录中。
setopt histignorespace
因此,我们可以按空格键,然后键入“ echo hi”,按Enter键,然后按向上箭头键,“ echo hi”就不在我们的历史记录中了:)。
注意别名“忘记”如何在my_remove_last_history_entry之前有一个空格。这样zsh不会将我们的“忘记”保存到历史记录中。
功能说明
ZSH使用fc作为历史记录或其他内容,因此我们执行'fc -W'将当前命令写入历史记录文件,而我们使用'head -n -1'将文件中的最后一个命令修剪掉。我们将该输出保存到一个临时文件,然后用临时文件替换原始历史文件。最后用fc -R重新载入历史记录。
但是,使用别名修复的功能存在问题。
如果我们通过函数名称运行函数,它将删除最后一个命令,即对函数的调用。这就是为什么我们将别名与空格一起使用的原因,因此zsh不会将此函数名称添加到历史文件中,从而使最后一项成为我们想要的:D。