计算目录树中的文件数量

计算目录树中的文件数量

对于备份程序的一致性检查,我想定义一个函数来计算目录中的所有文件,包括子目录、子子目录等中的所有文件。

到目前为止我正在尝试的解决方案如下:

countfiles() {
  local cdir=$1
  local files=$(ls -la $cdir | grep -cv '^[dl]')

  local dirstring=$(ls -la $cdir | grep '^d' | egrep -o ' \.?[^[:space:].][^[:space:]]+$')
  local directories=(${dirstring//"\n"/})

  echo ${directories[@]}


  for dir in ${directories[@]}; do
    echo -n "$dir "
    echo -n 'filecount >> '
    local dirfiles=$(countfiles "$cdir/$dir")
    echo -n $dirfiles
    echo ' <<'
    #files=$(($files+$dirfiles))
  done

  echo $files

}

这给了我以下输出:

.config .i3 .scripts
.config filecount >> gtk-3.0 termite gtk-3.0 filecount >> 2 << termite filecount >> 2 << 1 <<
.i3 filecount >> 5 <<
.scripts filecount >> 2 <<
5

虽然我的计数器的实现$files是在 atm 上注释的,并且我可能需要将其取消本地化,但现在我将所有变量设置为本地变量以避免任何干扰。

目录树如下:

/.scripts/backup_dotfiles.sh
/.config/termite/config
/.config/gtk-3.0/settings.ini
/.i3/config
/.i3/i3blocks.conf
/.i3/lockicon.png
/.i3/lockscreen.sh
/.gtkrc-2.0
/.bashrc
/.zshrc
/.i3
/.Xresources

我的问题:

  • 为什么除了主目录之外的文件总是+1?
  • 为什么它会计算“.config”目录中的任何内容,因为那里没有文件?
  • 我怎样才能解决这个问题?

答案1

您可能只想使用find.假设您的文件名称中没有换行符,只需执行以下操作:

find "$dir" -type f | wc -l

-type f匹配常规文件,但不匹配目录、管道、套接字等。

通常的输出find用换行符分隔文件名,因此如果任何名称包含换行符,输出将不明确。使用 GNU find,类似这样的事情可以工作:

find "$dir" -type f -printf . | wc -c

它只find为每个文件打印一个点,并计算点的数量。

其他版本find没有,-printf但我们可以使用用双斜杠传递输入路径的技巧。它们被视为单个斜杠,但不会自然地出现在输出中,因为文件名不能包含斜杠。然后计算输出中的双斜杠数量:

find "$dir//" -type -f | grep -c //

如果我们想纯粹使用 shell 脚本来做到这一点,我们可以让 shell 列出文件名,无需使用ls,例如在 Bash 中:

#!/bin/bash
files=0
shopt -s dotglob
countfiles() {
        local f;
        for f in * ; do 
                if [ -f "$f" ] ; then          # count regular files
                        files=$((files + 1))
                elif [ -d "$f" ] ; then        # recurse into directories
                        cd "$f"
                        countfiles
                        cd ..
                fi
        done
}
cd "$1"
countfiles
echo $files

答案2

您可以使用以下命令获取目录和子目录中的文件数:

 find path_to_directory -type f | wc -l

答案3

为什么除了主目录之外的文件总是+1?

因为 ls -la 还将字符串添加total 20到输出中。我可以看到,对于“master”目录,它还显示+1 值。

为什么它会计算“.config”目录中的任何内容,因为那里没有文件?

同样的原因。total ..产生的字符串ls

我怎样才能解决这个问题?

不要使用你的脚本:)我的意思是,它真的太复杂了。我们find这里过得很好。您的所有脚本都会变成类似的内容(如果您需要每个目录的文件):

find $yourdir -type d | while read dir ; do 
    echo "$dir == $(find $dir -maxdepth 1 -type f | wc -l) files" ; 
done

或者只是(如果您需要总和值):

find $yourdir -type f | wc -l

相关内容