find . -maxdepth 1 -type d | while read -r dir
do printf "%s:\t" "$dir"; find "$dir" -type f | wc -l; done
Thanks to Gilles and xenoterracide for safety/compatibility fixes.
The first part:
find . -maxdepth 1 -type d will return a list of all directories in the current working directory.
-maxdepth is a GNU extension
and might not be present in non-GNU versions of
This is piped to...
The second part:
while read -r dir; do
(shown above as
while read -r dir(newline)
do) begins a
while loop – as long as the pipe coming into the
while is open (which is until the entire list of directories is sent), the
read command will place the next line into the variable
dir. Then it continues...
The third part:
printf "%s:\t" "$dir" will print the string in
(which is holding one of the directory names) followed by a colon and a tab
(but not a newline).
The fourth part:
find "$dir" -type f makes a list of all the files
inside the directory whose name is held in
$dir. This list is sent to...
The fifth part:
wc -l counts the number of lines that are sent into its standard input.
The final part:
done simply ends the
So we get a list of all the directories in the current directory. For each of those directories, we generate a list of all the files in it so that we can count them all using
wc -l. The result will look like: