如何以目录作为参数运行一个命令,然后 cd 到同一目录?我得到“没有这样的文件或目录”

如何以目录作为参数运行一个命令,然后 cd 到同一目录?我得到“没有这样的文件或目录”

我想构造一个简短的函数来执行以下操作。假设我将文件“file.tex”移动到我的文档目录:

mv file.tex ~/Documents

然后,我想cd进入该目录:

cd ~/Documents

我想将其推广到任何目录,以便我可以这样做:

mv file.tex ~/Documents
follow

并让follow命令从前一个命令读取目标,然后相应地执行。对于一个简单的目录,这并不能节省太多时间,但是当使用嵌套目录时,如果能够使用

mv file.tex ~/Documents/folder1/subfolder1
follow

我认为这会相对简单,我可以做这样的事情:

follow()
{
    place=`history 2 | sed -n '1p;1q' | rev | cut -d ' ' -f1 | rev`
    cd $place
}

但这似乎不起作用。如果我 echo $place,我确实得到了所需的字符串(我正在使用 测试它~/Documents),但最后一个命令返回

No such file or directory

该目录确实存在。我不知所措。你能帮我一下吗?

答案1

您可以使用变量 来代替定义函数,$_该变量通过 扩展为上一个命令的最后一个参数bash。所以使用:

cd "$_"

mv命令后。

您也可以使用历史扩展:

cd !:$

如果必须使用函数:

follow () { cd "$_" ;}

$ follow () { cd "$_" ;}
$ mv foo.sh 'foo bar'
$ follow 
foo bar$ 

注意:这个答案针对的是您在处理位置参数时使用的确切命令行参数格式。对于其他格式,例如mv -t foo bar.txt,您需要事先合并特定的检查,那么包装器就合适了。

答案2

使用标准 bash 键绑定,该组合Alt.会将上一个命令行的最后一个参数复制到当前命令行中。所以,输入

$ mv foo ~/some/long/path/
$ cd <Alt><.>

会产生

$ mv foo ~/some/long/path/
$ cd ~/some/long/path/

甚至比单词 还要少打字follow

为了更加方便,重复Alt.组合将浏览所有先前命令行的最后一个参数。

附录:该组合键对应的 bash 命令名称为yank-last-arginsert-last-argument。它可以在 bash 联机帮助页的“Commands for Manipulated the History”下找到,或者在更详尽的Bash 参考手册.)

答案3

您几乎肯定会遇到波浪线扩展发生在参数扩展之前的问题,这可以通过一个简洁的示例来解释:

$ cd ~kaz
kaz $ var='~kaz'
kaz $ echo $var
~kaz
kaz $ cd $kaz
bash: cd: ~kaz: No such file or directory

这可以通过 来解决eval。无论如何,您将需要eval,因为您正在从历史记录中提取命令,并且它们可以包含任意扩展,例如:

$ mv file.tex ~/Documents/$(compute_folder_name foo-param)/subfolder1
$ follow

(存在一些问题,例如这些值的重新扩展可能不再与发生的原始扩展匹配。假设compute_folder_name是一个递增某些全局变量的函数。)

相关内容