bash find:获取找到的文件的目录

dub*_*elj 17 osx shell find

我有一个名为“parent_folder”的父文件夹,里面有很多子文件夹,在这些子文件夹中有一个名为“foo.mp4”的文件。

通过这样做,我可以轻松找到这些文件:

mymacbook:parent_folder username$ find ./ -name "foo.mp4" -exec echo {} \;
Run Code Online (Sandbox Code Playgroud)

现在返回每个文件的路径,相对于 parent_folder/

./path/to/foo.mp4
Run Code Online (Sandbox Code Playgroud)

我怎样才能只返回路径,而没有文件名?

Sté*_*las 26

随着GNU发现:

 find . -name foo.mp4 -printf '%h\n'
Run Code Online (Sandbox Code Playgroud)

对于其他finds,提供的目录名称不包含换行符:

 find . -name foo.mp4 | sed 's|/[^/]*$||'
Run Code Online (Sandbox Code Playgroud)

或者:

 find . -name foo.mp4 -exec dirname {} \;
Run Code Online (Sandbox Code Playgroud)

虽然这意味着dirname每个文件运行一个命令。

如果您需要在其上运行命令path,您可以执行以下操作(标准语法):

 find . -name "featured.mp4" -exec sh -c '
   for file do
     dir=${file%/*}
     ffmpeg -i "$file" -c:v libvpx -b:v 1M -c:a libvorbis "$dir" featured.webm
   done' sh {} +
Run Code Online (Sandbox Code Playgroud)

虽然在这种情况下,您可以使用-execdir(在 GNU 中也可用的 BSD 扩展find),它chdir()位于文件的目录中:

 find . -name "featured.mp4" -execdir \
   ffmpeg -i {} -c:v libvpx -b:v 1M -c:a libvorbis . featured.webm \;
Run Code Online (Sandbox Code Playgroud)

请注意,虽然 GNU 实现find将扩展{}./filename这里,但 BSD实现将扩展到filename. 在这里没问题,因为文件名作为参数传递给一个选项并且总是featured.mp4如此,但对于其他用法,您可能必须考虑到文件名可能以-or开头+(并被命令理解为选项)或包含=(例如,被 awk 理解为变量赋值),或导致此类问题的perl -p/n其他字符(尽管在这种情况下,并非所有这些字符都由 GNUfind./前缀修复)等,您可能需要考虑.