为什么“哪个myscript | xargs vim”运行良好?

时间:2017-06-13 21:09:09

标签: bash pipeline

为什么不

which myscript | xargs vim

工作得很好?当我退出vim时,我的终端(ubuntu 14.04)冻结了。

或者,有一个很好的清洁替代品吗?

1 个答案:

答案 0 :(得分:4)

为什么原件不起作用

如果您要将其用作交互式编辑器,那么您无法将任何输入到vim中:管道会覆盖stdin;编辑需要能够访问你的标准输入(除非是,通过X11进行交互 - 但这将是gvim)。

更详细一点:foo | bar同时运行foobarfoo的stdout连接到{{stdin} 1}}。因此,bar最初启动两个进程的shell which myscript | xargs vimwhich myscript - xargs vim的标准输出连接到which myscript的标准输入。< / p>

但是,这意味着xargs vim从用户输入的终端/控制台获取xargs vim而非的输入。因此,当which启动xargs vim时,vim继承的stdin也没有连接到终端 - 和vim,它是一个交互式编辑器,用于从终端的用户失败(可能是壮观或有趣的)。

做什么

vim

上面的vim "$(which myscript)" 语法是command substitution,它被运行的命令的stdout替换。因此,虽然这会覆盖$()的stdout(指向shell为了该替换而从中读取的FIFO),但它在任何方面都不会将输入和输出重定向到which

或者,如果确实想要使用vim(请注意以下使用xargs GNUism,以确保在传递带空格的文件名时它能正常工作 - 虽然不是带换行符的文件名):

-d

上面有which myscript | xargs -d $'\n' sh -c 'exec vim "$@" <&2' ,而不是直接运行vim,启动一个shell,它将stderr(文件描述符2)复制到stdin(文件描述符0,使用xargs重定向的默认目标),以及然后启动<,以便为你的stderr 提供附加到终端的stdin的vim文件描述符副本。 em>对您的TTY开放,请将vim替换为<&2