awkはいくつかの行を自動的にコピーします。誰かがこれを説明できますか?

awkはいくつかの行を自動的にコピーします。誰かがこれを説明できますか?

私のデータは次のとおりです。

A 4 G 1 G 1
C 4 C 2 C 2
T 6 T 5 T 5
A 6 T 2 T 2
C 6 T 2 T 2
T 6 G 2 G 2

私はコマンドを試しています:

awk -F " " '$1==$3 {$7=$6; print $0;}
            $1==$5 {$7=$4; print $0;}
            ($1 != $3 && $1 != $5) {$7=$2; print $0}' test.txt

データには5行しかありませんが、出力には7行があり、一部の行はランダムに繰り返されます。

どういうわけか、これはこのデータセットでのみ発生し、私が持っている他のデータセットでは発生しません。誰でも助けることができますか?何が起こったのか理解できません。

答え1

目的の動作方法を正確に説明していないので、ここでいくつかの推測をしましょう。

重複した行を見てください。

C 4 C 2 C 2

$1 は $3 と同じなので、最初のブロックが実行されます。 $ 1は$ 5に等しいので、2番目のブロックがトリガーされます。

入力ラインごとに1つの出力ラインだけが必要な場合は、データを1つの場所にのみ出力します。

awk -F " " '$1==$3 {$7=$6;}
            ($1==$5) {$7=$4; }
            ($1 != $3 && $1 != $5) {$7=$2}
            ($7 != "") { print $0 }' test.txt

私はこれがあなたが探している動作だと思いますが、入力と同じかより少ない数の出力ラインを生成します。すべての入力ラインに対して1ラインの出力が必要な場合は、最後のブロックから条件を削除します。

答え2

awk -F " " '$1==$3 {$7=$6; print $0;}
            $1==$5 {$7=$4; print $0;}
            ($1 != $3 && $1 != $5) {$7=$2; print $0}' test.txt

たとえば、とが両方とも真の場合、最初の$1==$32つの$1==$5ブロックはすべて実行され印刷されます。 2号線と3号線の場合です。両方のブロックは2つの異なるフィールドで$ 7を設定しますが、ここでは2行の値が同じです。

各行を最大1回だけ印刷するには、ブランチでフラグを設定し、そのフラグに従って印刷(または印刷しない)できます。たとえば、次のようになります。

awk -F " " '{ p=0; } 
            $1==$3 {$7=$6; p=1}
            $1==$5 {$7=$4; p=1}
            ($1 != $3 && $1 != $5) {$7=$2; p=1}
            p {print}' test.txt

print$0他の引数が指定されていない場合は印刷され、デフォルトの動作なpので、最後にコードブロックを実際に使用することはできません。

1同様に、各行を無条件に印刷するには、通常、次のような末尾のみが表示されます。awk '/.../ { ... } 1'

$7ただし、3つのブランチすべてがフィールドを異なる値に設定するため、フィールドをどのように処理するかを決定する必要があります。

ブロックの1つだけ(最大)実行する場合は、next各ブロック内のステートメントを使用して次の行に移動できます。

awk -F " " '$1==$3 {$7=$6; print; next}
            $1==$5 {$7=$4; print; next}
            ($1 != $3 && $1 != $5) {$7=$2; print; next}
           ' test.txt

...実際に条件を見ると、最初の2つの条件が偽の場合にのみ最後の条件が真のようです。したがって、すべてif-elseで書くことをお勧めします。

awk -F " " '{ if ($1==$3)      { $7=$6 };
              else if ($1==$5) { $7=$4 };
              else             { $7=$2 };
              print;
            }' test.txt

関連情報