我需要找到给定目录列表的空目录。有些目录中包含目录。
如果内部目录也是空的,我可以说主目录是空的,否则它不是空的。
我该如何测试?
例如:
A>A1(file1),A2 this is not empty beacuse of file1
B>B1(no file) this is empty
C>C1,C2 this is empty
我需要找到给定目录列表的空目录。有些目录中包含目录。
如果内部目录也是空的,我可以说主目录是空的,否则它不是空的。
我该如何测试?
例如:
A>A1(file1),A2 this is not empty beacuse of file1
B>B1(no file) this is empty
C>C1,C2 this is empty
Answers:
检查是否find <dir> -type f
输出任何东西。这是一个例子:
for dir in A B C; do
[ -z "`find $dir -type f`" ] && echo "$dir is empty"
done
-type f
是为了什么。
mkdir A B C A/A1 A/A2 B/B1 C/C1 C/C2; touch A/A1/file1
-并在我的答案中运行代码,它将报告OP要求的B和C为空。因此,您将需要比“它不起作用”更加具体。
这取决于您要对空目录执行的操作。当我希望删除树中所有空目录(例如test
目录)时,请使用以下命令。
find test -depth -empty -delete
关于上述命令,需要注意的一件事是,它还将删除空文件,因此请使用-type d选项来避免这种情况。
find test -depth -type d -empty -delete
拖放-delete
以查看匹配的文件和目录。
如果您对空目录树的定义是不包含任何文件,则您可以根据是否find test -type f
返回任何内容将某些内容组合在一起。
find
是一个非常有用的工具,RTFM经常并且经常真正地了解它可以做什么:-)
-empty
,太方便了!
find test -name ".DS_Store" -delete
请先运行,然后运行-empty delete
命令。另请注意,就像到pushd
父目录一样,因此find test
变为find .
,但是其余命令相同。
-depth
这里添加定义,即 查找原因以执行深度优先遍历,即以后顺序访问目录,并且目录中的所有条目将在目录本身之前起作用。我认为这是相关的。
您可以使用以下命令:
find . -type d -empty
find directory -mindepth 1 -type d -empty -delete
这是我发现最有趣的版本。如果从内部目录执行,它将删除下面的所有空目录(如果目录仅包含空目录,则该目录被视为空目录)。
mindepth选项可防止在目录为空时删除目录本身。
rmdir --ignore-fail-on-non-empty -p directory
摆脱父母。
find . -type d -empty
查找并列出当前树中的空目录和子目录。例如,空目录和子目录的结果列表:
./2047
./2032
./2049
./2063
./NRCP26LUCcct1/2039
./NRCP26LUCcct1/2054
./NRCP26LUCcct1/2075
./NRCP26LUCcct1/2070
在目录上不执行任何操作。它们只是列出。这对我有用。
为了只找到空目录(如问题标题中所指定),mosg的答案是正确的:
find -type d -empty
但是-empty
在非常老的find
版本上可能不可用(例如,HP-UX就是这种情况)。如果是这种情况,请参阅以下部分中描述的技术。目录是否为空?。
这有点棘手:假设目录MyDir
包含空目录。删除这些空目录后,MyDir
将成为一个空目录,也应将其删除。因此,我将命令rmdir
与选项--parents
(或-p
)一起使用,并在可能的情况下也删除了父目录:
find -type d -empty -exec rmdir -vp --ignore-fail-on-non-empty {} +
在较旧的find
版本上,+
尚不支持该语句,因此您可以;
改用:
find -type d -empty -exec rmdir -vp --ignore-fail-on-non-empty {} `;`
这些答案大多数都解释了如何检查目录是否为空。因此,我在这里提供了我所知道的三种不同的技术:
[ $(find your/dir -prune -empty) = your/dir ]
d=your/dir
if [ x$(find "$d" -prune -empty) = x"$d" ]
then
echo "empty (directory or file)"
else
echo "contains files (or does not exist)"
fi
变体:
d=your/dir
if [ x$(find "$d" -prune -empty -type d) = x"$d" ]
then
echo "empty directory"
else
echo "contains files (or does not exist or is not a directory)"
fi
说明:
find -prune
类似于少find -maxdepth 0
使用字符find -type d
仅打印目录find -empty
打印空目录和文件
> mkdir -v empty1 empty2 not_empty
mkdir: created directory 'empty1'
mkdir: created directory 'empty2'
mkdir: created directory 'not_empty'
> touch not_empty/file
> find empty1 empty2 not_empty -prune -empty
empty1
empty2
(( ${#files} ))
这个技巧是100%,bash
但是会调用(产生)一个子shell。这个想法来自Bruno De Fraine,并根据teambob的评论进行了改进。我建议如果您使用重击 并且您的脚本不必是可移植的。
files=$(shopt -s nullglob dotglob; echo your/dir/*)
if (( ${#files} ))
then
echo "contains files"
else
echo "empty (or does not exist or is a file)"
fi
注意:空目录和不存在的目录(即使提供的路径是文件)之间也没有区别。
[ $(ls -A your/dir) ]
此技巧的灵感来自nixCraft在2007年发布的文章。安德鲁·泰勒(Andrew Taylor)于2008年回答,gr8can8dian于2011年回答。
if [ "$(ls -A your/dir)" ]
then
echo "contains files"
else
echo "empty (or does not exist or is a file)"
fi
或单行Bashism版本:
[[ "$(ls -A your/dir)" ]] && echo "contains files" || echo "empty or ..."
注意: 当目录不存在时ls
返回$?=2
。但是文件和空目录之间没有区别。
rmdir -vp
因为我不仅需要删除根目录下的所有空目录,还需要删除文件后检查空目录和父目录,因此对我有很大帮助。在我的情况下,只要我不在要从中删除文件的树中,空目录就可以了。谢谢!
这个递归函数似乎可以解决问题:
# Bash
findempty() {
find ${1:-.} -mindepth 1 -maxdepth 1 -type d | while read -r dir
do
if [[ -z "$(find "$dir" -mindepth 1 -type f)" ]] >/dev/null
then
findempty "$dir"
echo "$dir"
fi
done
}
给定此示例目录结构:
。 |-dir1 / |-dir2 / | `-dirB / |-dir3 / | `-dirC / | `-file5 |-dir4 / | |-目录/ | `-file4 `-dir5 / `-dirE / `-dir_V /
运行该函数的结果将是:
./dir1 ./dir5/dirE/dir_V ./dir5/dirE ./dir5 ./dir2/dirB ./dir2
错过了/dir4/dirD
。如果移动递归调用findempty "$dir"
后fi
,功能将包括其结果目录。
如果目录为空(或不存在),则以下命令返回1,否则返回0(因此可以!
在Shell脚本中使用反转返回代码):
find $dir -type d -prune -empty -exec false {} +