Linux 如何计算每个目录中的文件数?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/15216370/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 19:11:30  来源:igfitidea点击:

How to count number of files in each directory?

linuxbashubuntu

提问by user784637

I am able to list all the directories by

我可以列出所有目录

find ./ -type d

I attempted to list the contents of each directory and count the number of files in each directory by using the following command

我尝试使用以下命令列出每个目录的内容并计算每个目录中的文件数

find ./ -type d | xargs ls -l | wc -l

But this summed the total number of lines returned by

但这总结了返回的总行数

find ./ -type d | xargs ls -l

Is there a way I can count the number of files in each directory?

有没有办法计算每个目录中的文件数?

采纳答案by glenn Hymanman

Assuming you have GNU find, let it find the directories and let bash do the rest:

假设你有 GNU find,让它找到目录,让 bash 做剩下的事情:

find . -type d -print0 | while read -d '' -r dir; do
    files=("$dir"/*)
    printf "%5d files in directory %s\n" "${#files[@]}" "$dir"
done

回答by Tuxdude

This should return the directory name followed by the number of files in the directory.

这应该返回目录名称,后跟目录中的文件数。

findfiles() {
    echo "" $(find "" -maxdepth 1 -type f | wc -l)
}

export -f findfiles

find ./ -type d -exec bash -c 'findfiles "
./ 6
./foo 1
./foo/bar 2
./foo/bar/bazzz 0
./foo/bar/baz 4
./src 4
"' {} \;

Example output:

示例输出:

find . -type f |
sed 's%/[^/]*$%%' |
sort |
uniq -c

The export -fis required because the -execargument of finddoes not allow executing a bash function unless you invoke bash explicitly, and you need to export the function defined in the current scope to the new shell explicitly.

export -f因为需要-exec的参数find不允许执行bash的功能,除非你调用bash的明确,以及你需要导出当前范围定义为新壳明确的功能。

回答by Jonathan Leffler

You could arrange to find all the files, remove the file names, leaving you a line containing just the directory name for each file, and then count the number of times each directory appears:

您可以安排查找所有文件,删除文件名,留下一行只包含每个文件的目录名,然后计算每个目录出现的次数:

find . -type f |
sed -e 's%^\(\./[^/]*/\).*$%%' -e 's%^\.\/[^/]*$%./%' |
sort |
uniq -c

The only gotcha in this is if you have any file names or directory names containing a newline character, which is fairly unlikely. If you really have to worry about newlines in file names or directory names, I suggest you find them, and fix them so they don't contain newlines (and quietly persuade the guilty party of the error of their ways).

唯一的问题是如果您有任何包含换行符的文件名或目录名,这是不太可能的。如果您真的必须担心文件名或目录名中的换行符,我建议您找到它们,并修复它们,使它们不包含换行符(并悄悄地说服有罪的一方承认他们的方式错误)。



If you're interested in the count of the files in each sub-directory of the current directory, counting any files in any sub-directories along with the files in the immediate sub-directory, then I'd adapt the sedcommand to print only the top-level directory:

如果您对当前目录的每个子目录中的文件数感兴趣,计算任何子目录中的任何文件以及直接子目录中的文件,那么我会将sed命令调整为仅打印顶级目录:

./dir1/dir2/file1

The first pattern captures the start of the name, the dot, the slash, the name up to the next slash and the slash, and replaces the line with just the first part, so:

第一个模式捕获名称的开头、点、斜线、直到下一个斜线和斜线的名称,并仅用第一部分替换该行,因此:

./dir1/

is replaced by

被替换为

find -type d -print0 | xargs -0 -n1 bash -c 'echo -n ":"; ls -1 "" | wc -l' --

The second replace captures the files directly in the current directory; they don't have a slash at the end, and those are replace by ./. The sort and count then works on just the number of names.

第二次replace直接捕获当前目录下的文件;它们末尾没有斜线,它们被替换为./. 然后排序和计数仅适用于名称的数量。

回答by Austin Phillips

Here's one way to do it, but probably not the most efficient.

这是一种方法,但可能不是最有效的。

./c/fa/l:0
./a:4
./a/c:0
./a/a:1
./a/a/b:0

Gives output like this, with directory name followed by count of entries in that directory. Note that the output count will also include directory entries which may not be what you want.

给出这样的输出,目录名后跟该目录中的条目数。请注意,输出计数还将包括可能不是您想要的目录条目。

du -a | cut -d/ -f2 | sort | uniq -c | sort -nr

回答by Sebastian Piskorski

This prints the file count per directory for the current directory level:

这将打印当前目录级别的每个目录的文件数:

find -type d -readable -exec sh -c 'printf "%s " ""; ls -1UA "" | wc -l' sh {} ';'

回答by o11c

Everyone else's solution has one drawback or another.

其他人的解决方案都有一个或另一个缺点。

  5 .
  4 ./aln
  5 ./aln/iq
  4 ./bs
  4 ./ft
  6 ./hot

Explanation:

解释:

  • -type d: we're interested in directories.
  • -readable: We only want them if it's possibleto list the files in them. Note that findwill still emit an error when it tries to search for more directories in them, but this prevents calling -execfor them.
  • -exec sh -c BLAH sh {} ';': for each directory, run this script fragment, with $0set to shand $1set to the filename.
  • printf "%s " "$1": portably and minimally print the directory name, followed by only a space, not a newline.
  • ls -1UA: list the files, one per line, in directory order (to avoid stalling the pipe), excluding onlythe special directories .and ..
  • wc -l: count the lines
  • -type d:我们对目录感兴趣。
  • -readable:如果可以列出其中的文件,我们只需要它们。请注意,find当它尝试在其中搜索更多目录时仍会发出错误,但这会阻止调用-exec它们。
  • -exec sh -c BLAH sh {} ';': 对于每个目录,运行此脚本片段,$0设置为sh$1设置为文件名。
  • printf "%s " "$1": 可移植且最少打印目录名称,后跟仅一个空格,而不是换行符。
  • ls -1UA: 列出文件,每行一个,按目录顺序(避免管道阻塞),排除特殊目录...
  • wc -l: 计​​算行数

回答by Giddy

find . -type f -printf '%h\n' | sort | uniq -c

找 。-type f -printf '%h\n' | 排序 | uniq -c

gives for example:

例如:

for d in `find . -type d -print` 
do 
  echo -e "$d\t$(find $d -maxdepth 1 -type f -print | wc -l)"
done

回答by Sixhobbits

This can also be done with looping over ls instead of find

这也可以通过循环 ls 而不是 find 来完成

for f in */; do echo "$f -> $(ls $f | wc -l)"; done

for f in */; do echo "$f -> $(ls $f | wc -l)"; done

Explanation:

解释:

for f in */;- loop over all directories

for f in */;- 遍历所有目录

do echo "$f ->- print out each directory name

do echo "$f ->- 打印出每个目录名称

$(ls $f | wc -l)- call ls for this directory and count lines

$(ls $f | wc -l)- 为这个目录调用 ls 并计算行数

回答by sthames42

I tried with some of the others here but ended up with subfolders included in the file count when I only wanted the files. This prints ./folder/path<tab>nnnwith the number of files, not including subfolders, for each subfolder in the current folder.

我在这里尝试了其他一些文件,但当我只想要这些文件时,文件计数中包含了子文件夹。这将打印./folder/path<tab>nnn当前文件夹中每个子文件夹的文件数,不包括子文件夹。

for file in */; do echo "$file -> $(ls $file | wc -l)"; done | cut -d ' ' -f 3| py --ji -l 'numpy.sum(l)'

回答by Naga Venkatesh Gavini

This will give the overall count.

这将给出总体计数。

##代码##