Reputation: 21682
What I'm trying to do is to count json files in each folder.
My current attemp give total number of files, not per folder:
ls -d */ | xargs -I {} find {} -name "*.json" | wc -l
Upvotes: 1
Views: 1116
Reputation: 27340
The following command will recursively search all directories starting from the working directory. Directories containing at least one .json file will be listed with the number of json files in that directory.
find -type f -iname \*.json -exec dirname {} + | sort | uniq -c
This command assumes that all directories have single line names. It may fail in the rare case in which some directory's name contains a newline character. Some versions of dirname
, sort
, and uniq
support null delimiters to work around this issue. Add -z
to all of these commands.
To also print the directories which do not contain any json files, you could use the following command. This command also handles newlines in directory names and allows to customize the output format (just modify the echo
part).
shopt -s globstar nullglob
count() { echo "$#"; }
for d in ./ **/; do
echo "$(count "$d"*.json) $d"
done
$ tree
.
├── dir1
│ ├── dir3
│ │ ├── a.json
│ │ ├── b.json
│ │ ├── c.json
│ │ └── dir5
│ │ └── alsonotjson
│ └── dir4
├── dir2
│ ├── lorem.json
│ └── yadda.txt
├── notajsonfile
└── somejsonfile.json
5 directories, 8 files
$ find -type f -iname \*.json -exec dirname {} + | sort | uniq -c
1 .
3 ./dir1/dir3
1 ./dir2
$ shopt -s globstar nullglob; count() { echo "$#"; };
$ for d in ./ **/; do echo "$(count "$d"*.json) $d"; done
1 ./
0 dir1/
3 dir1/dir3/
0 dir1/dir3/dir5/
0 dir1/dir4/
1 dir2/
To only print the working directory as well as its non-recursive subdirectories, you can ...
-maxdepth 2
for the first command.**/
with a normal glob */
for the second command.$ find -maxdepth 2 -type f -iname \*.json -exec dirname {} + | sort | uniq -c
1 .
1 ./dir2
$ shopt -s nullglob; count() { echo "$#"; };
$ for d in ./ */; do echo "$(count "$d"*.json) $d"; done
1 ./
0 dir1/
1 dir2/
Upvotes: 3