Your command only counts the number of lines outputted from
find command will only output the pathnames of regular files in or under the
If you want to count the number of regular files and directories in or under your
documents directory you may do this in the
set -- documents/**/*(DN/) documents/**/*(DN.)
printf 'There are %d regular files and directories in or under "documents"\n' "$#"
This sets the positional parameters (
$2, etc.) to the result of expanding the two filenames globbing patterns
documents/**/*(DN.), the first of which will match all regular files while the second matches directories (no matter if they are hidden or not). The
** pattern matches "recursively" down into subdirectories.
Once the positional parameters have been set, the special variable
$# will hold the number of these parameters.
bash shell, which does not support the glob qualifiers
(DN.), you may use a loop:
shopt -s globstar dotglob nullglob
for pathname in documents/**/*; do
if [[ -f $pathname ]] || [[ -d $pathname ]]; then
[[ ! -h $pathname ]] && count=$(( count + 1 ))
printf 'There are %d regular files and directories in or under "documents"\n' "$count"
This is slightly more involved than the
zsh variation, but should be easy to follow. We first set a number of shell options so that we can use
**, so that we count hidden names, and so that the pattern resolves to nothing if there are no matches (these last two equates to the
D and the
N in the
zsh glob qualifier).
Inside the loop, we test whether the current pathname is a regular file or a directory, and not a symbolic link. If it's a regular file or directory, we count it.
sh, you have to resort to
find documents \( -type f -o -type d \) -exec echo . \; | wc -l
We look for regular files or directories in or under
documents, and for each such thing we output a dot on a line by itself. The
wc -l then counts the number of lines produced. This avoids counting filenames with embedded newlines multiple times.
Note that this variation will also count the
documents directory itself.