让 xargs 为每个输入运行一次命令,而不是每个输入都运行一次

让 xargs 为每个输入运行一次命令,而不是每个输入都运行一次

我以为我可以运行以下命令

find ./ -iname "*\.mkv" | xargs -d "\n" ffprobe -show_streams -i

获取每个文件的编解码器信息,但看起来 xargs 试图将找到的每个文件名传递给 ffprobe,而不是对每个输入运行一次 ffprobe。

运行时我收到此错误

参数 './Canadian.Bacon.1080p.mkv' 作为输入文件名提供,但 './The Big Short.(2015)/The Big Short (2015) Remux-1080p.mkv' 已经指定。

答案1

要对找到的每个文件运行一次调用,最好直接使用命令find本身的-exec功能:

find ./ -iname '*.mkv' -exec ffprobe -show_streams -i {} \;

真正的重点是每次调用时传递多个参数。您可以通过添加(或如果分隔符是换行符)来xargs让它运行单个参数-n 1-L 1

find ./ -iname '*.mkv' | xargs -d '\n' -n 1 ffprobe -show_streams -i

或者

find ./ -iname '*.mkv' | xargs -d '\n' -L 1 ffprobe -show_streams -i

添加一个显式替换字符串-I{}也可以,因为-I 暗示 -L 1。同样,如果您已经使用-d '\n'来防止文件名被空格和制表符分割,您也可以尽全力允许文件名包含换行符,方法是将分隔符更改为空字符:

find ./ -iname '*.mkv' -print0 | xargs -r -0 -n 1 ffprobe -show_streams -i

如果您正在使用find,通常不需要xargs,即使您想要在每次调用时传递多个参数 - 有另一种形式{} +可以为您做到这一点:

find ./ -iname "*.mkv" -exec somecommand {} +

相关内容