複数の列に文字列がn回表示される行数の計算

複数の列に文字列がn回表示される行数の計算

私はタブで区切られた5つの列からなる何百ものテキストファイルを持っています。最初の列にはインデックスが含まれ、次の4つの列には発生回数が含まれます。ここで、値がゼロの3列(つまり、次の例では7行)を含む行数を計算しようとしています。

1   0   0   0   9
2   0   9   0   0
3   10  0   0   0
4   0   10  4   0
5   0   0   0   10
6   0   0   0   10
7   0   0   0   10
8   0   10  0   0
9   5   0   5   0

これをRからループにコーディングできますが、元のファイルにはそれぞれ6000万以上の行が含まれているので、awkまたはsedとwc -lを使用してこれを解決する方法がないかどうか疑問に思います。

ベストアンサー1

はい、次のことができますawk

awk '{ 
       k=0; 
       for(i=2;i<=NF;i++){ 
         if($i == 0){
             k++
         }
       }
       if(k==3){
         tot++
       }
      }
      END{
          print tot
      }' file 

また、(GNU)sedwc

$ sed -nE '/\b0\b.*\b0\b.*\b0\b/p' file | wc -l
7

しかし、個人的にはPerlを代わりに使用します。

$ perl -ale '$tot++ if (grep{$_ == 0 } @F) == 3 }{ print $tot' file 
7

または少し圧縮されていません。

$ perl -ale 'if( (grep{$_ == 0 } @F) == 3 ){
                  $tot++ 
              }
              END{
                  print $tot
              }' file 
7

そしてあなたのゴルファーのために:

$ perl -ale '(grep{$_==0}@F)==3&&$t++}{print$t' file
7

説明する

  • -ale-aPerlをawkのように振る舞います。入力ファイルの各行を読み、それをスペースで分割して配列にします@F。各呼び出しに対する入力の末尾の改行を-l追加および削除し、各入力行に適用する必要があるスクリプト。\nprint-e
  • $tot++ if (grep{$_ == 0 } @F) == 3$tot正確に3つのフィールドがあるたびに1ずつ増加します0。最初のフィールドは1から始まるので、0にはならないことがわかっているので、除外する必要はありません。
  • }{END{}:これは、ファイルが処理された後に実行されるコードブロックを提供する簡単な方法です。したがって、}{ print $tot値を含む3つのフィールドを含む行の総数が印刷されます0

おすすめ記事