我想找到所有包含的目录两个都aMakefile
和 a 匹配的文件*.tex
。命令find
或locate
很容易找到其中一个。但是如何合并或交叉这些结果,以产生所需的目录?
一个有用的答案可以推广到其他文件名。甚至更好的是,它可以合并两个以上的此类查询。
(我不知道如何应用的find
布尔运算符,例如“and” expr1 -a expr2
。对于也是如此locate -A
。也许进行两次搜索,删除文件名并保留路径,,sort -u
进入comm -12 <(cmd1) <(cmd2)
?)
答案1
只需使用-a
‘AND’条件:
find . -type d -exec test -f {}/Makefile \; -a -exec bash -c 'compgen -G '{}'/*.tex >/dev/null;exit $?' \; -print
慢动作:
-exec test -f {}/Makefile \;
检查Makefile
目录中是否存在-exec bash -c 'compgen -G '{}'/*.tex >/dev/null;exit $?'
*.tex
检查目录中是否有任何文件- 仅当两个测试都为真时,整行测试才为真
- 在这种情况下打印目录名称
跑在:
./no1
./no1/yes3
./no1/yes3/foo.tex
./no1/yes3/Makefile
./no1/no3
./no1/no
./no1/Makefile
./q
./no2
./no2/foo.tex
./yes1
./yes1/foo.tex
./yes1/Makefile
./yes2
./yes2/foo.tex
./yes2/Makefile
给出:
./no1/yes3
./yes1
./yes2
答案2
find
无法执行“子查询”来打印包含某些文件的目录,因此comm
确实是可行的方法:
comm -12 <(find . -name Makefile -exec dirname {} \; | sort ) <(find . -name '*.tex' -exec dirname {} \; | sort)
您还可以循环遍历目录(使用递归方式globstar
)可能会更快(compgen
来源):
for directory in */
do
if [ -e "${directory}/Makefile" ] && compgen -G "${directory}/"*.tex > /dev/null
then
printf '%s\n' "${directory}"
fi
done