ext4で深く入れ子になったフォルダの「コスト」はいくらですか?

ext4で深く入れ子になったフォルダの「コスト」はいくらですか?

ワイルドカードマッチングを実行する必要がある場合、単一のディレクトリにある数十万のファイルでパフォーマンスの問題が発生します。私のアプリケーションの観点から見ると、簡単な解決策はファイルを深く入れ子になったフォルダに配置することです。

階層全体のフォルダの総数の推定上限は9^30です。この制限に達したことがないと仮定できます(以下の説明を参照)。ファイルが追加されるほど、フォルダの数は増えます。

Q:ext4ファイルシステムに多数のフォルダを作成すると、ファイルシステムの観点からどのような影響がありますか?たとえば、どのくらいのスペースが消費されるかです。他のフォルダのみを含むフォルダ?メタデータが多すぎると問題が発生しますか?

(私のアプリケーションの観点から見ると、上記の構造は、より単純な階層のハッシュベースのフォルダに比べて特定の利点があり、データを整理する「より良い」方法を知っています。)

答え1

各フォルダは、1つのinode(256バイト)と少なくとも1つのブロック(4096バイト)を占有します。より大きな問題は、複数の階層レベルのアクセス時間である可能性があります。

パフォーマンスの問題は、フォルダのサイズではなく、パス名の拡張によって発生する可能性があります。パス名の拡張には2つの問題があります。

  1. 結果を並べ替えます(無効にすることはできません)。これは、大量のプロジェクトに不便な時間がかかります。
  2. (使用タイプに応じて)無効なコマンドライン(アイテムが多すぎる)を生成します。

この問題はアプリケーションレベルで解決する必要があります。一度に100個のファイル名を読み取り(ソートされていない、findまたは使用ls -U)、必要に応じてグループをソートします。また、ディスクとCPU使用率を並列に読み取ることができます。

パス名の拡張および/またはソートが本当に必要な場合は、ファイルを対応する(空の)ディレクトリにソートされた順序で追加することで、プロセスの速度を大幅に向上させることができます(ファイルがほとんど変更されない場合)。

答え2

Ext4は以前のバージョンよりも大きなディレクトリを少し上手く処理しますが、同じディレクトリに10,000個のファイルがある場合はまだ輻輳する可能性があります。ディレクトリ階層から複数のレベルにファイルを分割することは、パフォーマンスを維持するための一般的なソリューションです。各深さの増加には、ファイルを見つけるときに追加の間接参照が必要ですが、幅は深さに応じて指数関数的に増加します。

たとえば、ファイル名が文字、数字、および一部の句読点で構成されている場合は、それらをすべて同じディレクトリに配置するのではなく、ファイル名の最初の2文字に基づいてサブディレクトリを作成します。つまり、ファイルはfoobarに保存されますfo/foobar。サブディレクトリにまだファイルが多すぎる場合は、深さを増やしてくださいfo/ob/foobar。分割する文字数と停止する深さを決定するには、ベンチマークを実行する必要があります。

潜在的なディレクトリはたくさんありますが、ほとんどは空になります。したがって、最初からすべてのディレクトリを作成するのではなく、必要に応じて作成してください。たとえば、ファイルを作成する必要がある場合は、ディレクトリがまだ存在しない場合は作成し、foobar同じ操作foを実行して保存します。fo/bafoobarfo/ba/foobar

ファイルが非常に小さくない限り(4kB未満)、ディレクトリが占めるスペースは無視できます。ファイルが小さくても深さが過剰でない限り、ディレクトリにはファイルよりはるかに少ないファイルが含まれます。ただし、小さなファイルが多い場合はデータベースを使用する必要があります。

関連情報