让xargs对占位符{}进行单词拆分

5
(虽然在Bash中,单词分割有一个特定的定义,但在本文中它表示按空格或制表符分割。)
使用这个输入演示xargs的问题:
$ cat input.txt
LineOneWithOneArg
LineTwo WithTwoArgs
LineThree WithThree Args
LineFour  With  Double  Spaces

并且这个Bash命令用于回显传递给它的参数,

$ bash -c 'IFS=,; echo "$*"' arg0 arg1 arg2 arg3
arg1,arg2,arg3

注意,xargs -L1 如何将每行拆分为多个参数。

$ xargs <input.txt -L1 bash -c 'IFS=,; echo "$*"' arg0
LineOneWithOneArg
LineTwo,WithTwoArgs
LineThree,WithThree,Args
LineFour,With,Double,Spaces

然而,xargs -I{} 将整行作为单个参数扩展成 {}

$ xargs <input.txt -I{} bash -c 'IFS=,; echo "$*"' arg0 {}
LineOneWithOneArg
LineTwo WithTwoArgs
LineThree WithThree Args
LineFour  With  Double  Spaces

虽然在大多数情况下这是完全合理的行为,但有时候我们更喜欢单词分割的行为(第一个xargs示例)。

而且,虽然xargs -L1可以被视为一种解决方法,但它只能用于将参数放置在命令行的末尾,这使得表达变得不可能。

$ xargs -I{} command first-arg {} last-arg

使用xargs -L1命令可以实现该功能。(当然,如果command能够按不同顺序接受参数,例如选项时,情况可能会有所不同。)

是否有办法使xargs -I{}在扩展{}占位符时拆分每行文本?

1个回答

5
有点儿相似。
echo -e "1\n2 3" | xargs sh -c 'echo a "$@" b' "$0"

输出:

a 1 2 3 b

参考资料:https://dev59.com/tmUq5IYBdhLWcg3wQ-Xk#35612138

此外:

echo -e "1\n2 3" | xargs -L1 sh -c 'echo a "$@" b' "$0"

输出:

a 1 b
a 2 3 b

啊,有趣……这种方法通过将要被xargs执行的命令包装在一个shell中来解决问题,因此xargs会将参数传递给shell。然后shell脚本通过$@变量引用单词分割的参数。聪明! - mxxk
谢谢!但是等一下,你不是想在这种情况下得到两个结果吗? a 1 ba 2 3 b - webb
这实际上是一个完美的解决方案,使用shell包装器和$@一起。你是指其他什么吗? - mxxk
1
我不确定你想要我的示例输出是一行上的 a 1 2 3 b 还是分别在两行上的 a 1 ba 2 3 b,因此我编辑了我的答案以包括这两个选项。 - webb
1
啊,谢谢你澄清。在我的原始示例中,我使用了-L1-I{},它们都需要每个命令调用消耗一行输入。当然,拥有其他选择也无妨。 - mxxk

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接