我找到了一种使用 find -exec 将多个文件集中在一行中的方法,如 xargs,但我不确定它到底是如何工作的

I've found a way to use find -exec to cp multiple files all in one line like xargs, but I'm not sure exactly how it works

我一直在使用 find -exec 和 find | xargs 在过去几个小时的探索和试验中,现在我发现了一个我在其他地方从未见过的命令变体。

例如这个查找命令获取子目录下的所有文件并将它们复制到当前目录

find . -type f -regex './[^\.].*/[^.*].*' -exec sh -c 'cp "$@" .' thiscanbeanything {} +

将全部在一行上执行,如下所示:

cp ./testy/bar ./testy/baz ./testy/foo .

而不是通常的:

find . -type f -regex './[^\.].*/[^.*].*' -exec sh -c 'cp {} .' \;

在多行上执行

cp ./testy/bar .
cp ./testy/baz .
cp ./testy/foo .

此外,在第一个命令中,输出将仅为:

cp ./testy/baz ./testy/foo .

除非 sh -c 'cmd' 后面跟着其他东西,在我的示例中是 thiscanbeanything.

有人可以阐明发生了什么,或者这是否可行?

要了解发生了什么,请看一下:

$ sh -c 'echo 0=[=10=] 1= 2=' thiscanbeanything one two
0=thiscanbeanything 1=one 2=two

这将使用选项 -c 'echo 0=[=12=] 1= 2=' 和三个参数 thiscanbeanything one two.

执行 sh

通常,[=14=]是正在执行的脚本的名称。当 运行 sh -c 时,没有脚本,但名称取自您提供的第一个参数,在本例中为 thiscanbeanything

文档

此行为记录在 man bash-c 选项下:

-c string
If the -c option is present, then commands are read from string. If there are arguments after the string, they are assigned to the positional parameters, starting with [=19=].