GNU/Linux >> Linux の 問題 >  >> Linux

AWK を使用して 2 つのファイルをマージする方法は?

ありがたいことに、これをまったく書く必要はありません。 Unix には、これを行うための join コマンドがあります。

join -1 1 -2 1 File1 File2

これが「実行中」です:

will-hartungs-computer:tmp will$ cat f1
4050 S00001 31228 3286 0
4050 S00012 31227 4251 0
4049 S00001 28342 3021 1
4048 S00001 46578 4210 0
4048 S00113 31221 4250 0
4047 S00122 31225 4249 0
4046 S00344 31322 4000 1
will-hartungs-computer:tmp will$ cat f2
4050 12.1 23.6
4049 14.4 47.8   
4048 23.2 43.9
4047 45.5 21.6
will-hartungs-computer:tmp will$ join -1 1 -2 1 f1 f2
4050 S00001 31228 3286 0 12.1 23.6
4050 S00012 31227 4251 0 12.1 23.6
4049 S00001 28342 3021 1 14.4 47.8
4048 S00001 46578 4210 0 23.2 43.9
4048 S00113 31221 4250 0 23.2 43.9
4047 S00122 31225 4249 0 45.5 21.6
will-hartungs-computer:tmp will$ 

$ awk 'FNR==NR{a[$1]=$2 FS $3;next}{ print $0, a[$1]}' file2 file1
4050 S00001 31228 3286 0 12.1 23.6
4050 S00012 31227 4251 0 12.1 23.6
4049 S00001 28342 3021 1 14.4 47.8
4048 S00001 46578 4210 0 23.2 43.9
4048 S00113 31221 4250 0 23.2 43.9
4047 S00122 31225 4249 0 45.5 21.6
4046 S00344 31322 4000 1

説明:(部分的に別の質問に基づいています。しかし、少し遅れています。)

FNR 現在のファイルのレコード番号 (通常は行番号) と NR を参照します 総レコード数を指します。演算子 ==は比較演算子で、周囲の 2 つのオペランドが等しい場合に true を返します。だから FNR==NR{commands} 括弧内のコマンドは、最初のファイルの処理中にのみ実行されることを意味します (file2

FS フィールドセパレータと $1 を参照します 、 $2 などは、行の 1 番目、2 番目などのフィールドです。 a[$1]=$2 FS $3 辞書(/配列) (名前は a ) は $1 で埋められます キーと $2 FS $3

; コマンドを区切ります

next は、現在の行で他のコマンドが無視されることを意味します。 (処理は次の行に続きます。)

$0 行全体です

{print $0, a[$1]} 行全体と a[$1] の値を出力するだけです ( $1 の場合 は辞書にあります。それ以外の場合は $0 のみです 印刷されます)。 2 番目のファイル (file1) に対してのみ実行されるようになりました。 現在)、FNR==NR{...;next} のため .


ファイル 2 のエントリを、BEGIN ブロック内の連想配列のペアに読み込む必要があります。 GNU Awk を想定:

BEGIN { while (getline < "File 2") { f[$1] = $2; g[$1] = $3 } }

メイン処理ブロックでは、ファイル 1 から行を読み取り、BEGIN ブロックで作成された配列から正しいデータを出力します:

{ print $0, f[$1], g[$1] }

ファイル 1 をファイル名引数としてプログラムに指定します。

awk 'BEGIN { while (getline < "File 2") { f[$1] = $2; g[$1] = $3 } }
     print $0, f[$1], g[$1] }' "File 1"

ファイル名にはスペースがあるため、ファイル名の引数を引用符で囲む必要があります。 getline を囲む引用符が必要です 変数名になるため、スペースが含まれていなくてもファイル名を変更します。


Linux
  1. Cpanelでファイルマネージャーを使用してファイルをアップロードする方法

  2. wget vs curl:wget と curl を使用してファイルをダウンロードする方法

  3. 「dd」コマンドを使用して Linux でスパース ファイルを作成する方法

  1. tar を使用してフォルダー構造のないファイルを抽出するにはどうすればよいですか

  2. 2 つのファイルを 1 行ずつ一貫してマージする方法

  3. awkを使用してファイルをインプレースで変更するには? (sed -i と同様)

  1. LKM を使用して C プログラムで Linux proc ファイルを作成する方法

  2. diff を使用して 2 つのファイルを手動でマージする

  3. 2 つの HTML ファイルをマスター HTML ファイルにマージする