Bash で子ディレクトリを再帰的に検索し、ファイルサイズが大きい順にリストアップする

Bash で、あるディレクトリ配下の全てのファイルを対象に、ファイルサイズが大きい順でリストアップしたいなと思った。サラッと出来るんじゃね?と思ったら案外面倒だった…。

目次

ディレクトリ直下だけで良ければ ls -S

ディレクトリの直下のファイル群なら、以下のように ls コマンドだけで「ファイルサイズが大きい順」にリストアップできる。

# -S オプションがファイルサイズの大きい順に並べ替えてくれる
$ ls -lS

# ヒューマンリーダブルな単位で表示させるなら -h オプションを付ける
$ ls -lSh

今回は、配下の子ディレクトリ・孫ディレクトリの下にあるファイルまで、再帰的に検索対象としたかったので、コレだとちょっと不足。

指定のサイズ以上のファイルを列挙したければ find -size

1MB 以上のファイルだけ抽出したい、といった形なら、次のようにしてやると良い。

$ find . -size +1M | xargs -I {} ls -lah {} | sort -rn

find コマンドの -size オプションで、「1M 以上」とか「500k 以上」みたいな指定ができる。

その結果を ls -lah で表示した後、sort -rn で数字の降順でソートする。コレで、指定以上のサイズのファイルを列挙できた。

しかしコレだと、最初に「1MB 以上」みたいな指定をしないといけなくて、ちょっとやりたいことと違う。

du を使う → ディレクトリが除外できていない

$ du -ah | sort -rh

こんなイディオムも見付けたが、コチラは「ディレクトリ」も対象になってしまっていて、「重たいファイルが含まれる親ディレクトリ」が上位に並んでしまう。ちょっと微妙。

コレが正解

ついに見付けた正解はコチラ。

$ find . -type f -exec du -ah {} + | sort -rh

コレで、配下のディレクトリを再帰的に検索しつつ、ディレクトリは除外してファイルのみを対象にし、ファイルサイズが大きい順に並べて出力できた。

↑ コチラは 9.9M とか 16K とかいうように、ヒューマンリーダブルな単位でファイルサイズが表示される。

以下のように du を使わず、find コマンドの -printf オプションを使う方法も発見した。コチラは Mac の場合は gfind (GNU find) を使わないと「find: -printf: unknown primary or operator」エラーが出るので注意。

$ find . -type f -printf '%s\t%p\n' | sort -rn

コレでよきよき。