
私の入力ファイルにはコロンで区切られたフィールドがあります。
基本:
one:111:222:333
fiv:333:222:333
two:123:234:500
ファイル1:
one:111:222:333
two:123:234:501
ファイル2:
one:111:222:333
thr:-:234:232
fiv:999:500:232
ヒントありがとう協会awkコードをいくつか修正しました。
$ awk -F':' -vf=main 'FILENAME==f{m=$0};FILENAME!=f&&$2~/[0-9]+/{if ($2~/[0-9]+/&&(!($1 in a) || $3 > a[$1])) { a[$1] = $3; b[$1] = $0 } next;}{if (($1 in a) && (a[$1] > $3)){ print b[$1]":updated:"m; delete b[$1] } else print; }' file* main
thr:-:234:232
one:111:222:333
fiv:999:500:232:updated:fiv:333:222:333
two:123:234:500
なぜ行を印刷するのですthr:-:234:232
か?thr
デフォルトファイルでは何も起こらないので、そのファイルのすべての更新は無視する必要があります。更新は、基本ファイル内の最初の列の行とfile1またはfile2に存在し、3番目の列に大きい値を持つ最初の列に対応する行のみに基づいている必要があります。
ここではなぜ$2~/[0-9]+/
動作しませんか?
更新:まだわからない。以下を見てください。
テストメインファイルを次のように変更した場合:
one:111:222:333 fiv:333:222:333 two:123:234:500 ten.233:422:452
そして、次のawkコマンドを実行してください。
$ awk -F':' -vf=main 'FILENAME==f{m=$0};FILENAME!=f&&$2~/[0-9]+/{if ($2~/[0-9]+/&&(!($1 in a) || $3 > a[$1])) { a[$1] = $3; b[$1] = $0 } next;}{if (($1 in a) && (a[$1] > $3)){ print b[$1]":updated:"m; delete b[$1] } else print; }' file* main
thr:-:234:232
one:111:222:333
fiv:999:500:232:updated:fiv:333:222:333
two:123:234:500
ten.233:422:452
したがって、thr行はファイルにthr
ないため、出力にはならないため、出力が間違っています。main
追加の条件を追加してコマンドを変更しましたが、else if($1 in a) {print};
デフォルトファイルに「ten」で始まる行は印刷されません。
$ awk -F':' -vf=main 'FILENAME==f{m=$0};FILENAME!=f&&$2~/[0-9]+/{if ($2~/[0-9]+/&&(!($1 in a) || $3 > a[$1])) { a[$1] = $3; b[$1] = $0 } next;}{if (($1 in a) && (a[$1] > $3)){ print b[$1]":updated:"m; delete b[$1] } else if($1 in a) {print}; }' file* main
one:111:222:333
fiv:999:500:232:updated:fiv:333:222:333
two:123:234:500
どんな助けでも本当に感謝します。
awkは本当に素晴らしいです。残念ながら、私はプログラマーではないので、まだ自分自身を見つけることができません。
答え1
next
ブロックに条件があるためですFILENAME != f && $2 ~ /[0-9]+/
。行がthr
その条件を満たしていないため、「すべての行」ブロックに属します。そこには$ 1が存在しないため、a
ブロックelse
が入力され、対応する行が印刷されます。
私はあなたが実際にプログラムを見ることができるように合理的なインデントを使用している場合、これを自分で理解できると思います。
awk -F':' -vf=main '
FILENAME == f {m = $0}
FILENAME != f && $2 ~ /[0-9]+/ {
if ($2 ~ /[0-9]+/ && (!($1 in a) || $3 > a[$1])) {
a[$1] = $3
b[$1] = $0
}
next
}
{
if (($1 in a) && (a[$1] > $3)) {
print b[$1]":updated:"m
delete b[$1]
} else
print
}
' file* main