大容量ファイルのパフォーマンス向上

大容量ファイルのパフォーマンス向上

300,000行以上のFILE_Aと30,000行以上のFILE_Bがあります。 FILE_Aの各行をFILE_Bにgrepし、grepの結果を新しいファイルに書き込むbashスクリプトを作成しました。

全体のプロセスは5時間以上かかります。

私のスクリプトのパフォーマンスを向上させる方法があると思うなら、どんな提案でも探しています。

grep コマンドとして grep -F -m 1 を使用します。 FILE_Aは次のとおりです。

123456789 
123455321

FILE_Bは次のようになります。

123456789,123456789,730025400149993,
123455321,123455321,730025400126097,

したがって、bashには、FILE_Aで次の行を選択し、FILE_Bでgrepするwhileループがあります。 FILE_Bでパターンを見つけたら、result.txtに書き込みます。

while read -r line; do
   grep -F -m1 $line 30MFile
done < 300KFile

ご協力ありがとうございます。

ベストアンサー1

パフォーマンスの鍵は、大容量ファイルを一度だけ読むことです。

複数のパターンを別々の行に配置して grep に渡すことができます。これは通常、grepにファイルからパターンを読み取るように指示することによって行われます。

grep -F -f 300KFile 30MFile

これにより、大きなファイル全体で一致を順番に出力し、複数のパターンに一致する行のみを一度だけ印刷します。また、これは行のどこでもパターンを探します。たとえば、パターンファイルに含まれている場合と1234などの行が一致します。123456,345678,2348962342478912,1211138,1234

前処理パターンにより、正確な列の一致を制限できます。たとえば、パターンに特殊文字が含まれていない場合()?*+\|[]{}:

<300KFile sed -e 's/^/(^|,)/' -e 's/$/($|,)/' |
grep -E -f - 30MFile

各パターンの最初の一致のみを維持することが重要な場合は、最初のパスを作成して上記の関連行のみを抽出し、awkまたはPerlで2番目のパスを作成してどのパターンが表示されたかを追跡します。

<300KFile sed -e 's/^/(^|,)/' -e 's/$/($|,)/' |
grep -E -f - 30MFile |
perl -l -F, -ape '
    BEGIN {
        open P, "300KFile" or die;
        %patterns = map {chomp; $_=>1} <P>;
        close P;
    }
    foreach $c (@F) {
        if ($patterns{$c}) {
            print;
            delete $patterns{$c};
        }
    }
'

おすすめ記事