特定のレコードのフィールド区切り記号()のみを変更し、FS
新しいフィールド区切り文字を使用してレコード($0
)、フィールド($N
)、およびフィールド数()を再計算しようとしています。NF
しかし、これはうまくいかないようです。
例:これには、スペースで区切られた3つのフィールドとして解釈される行があります。フィールド区切り文字をに変更してn
レコード($1 = $1
)を強制的に書き換えると、次の印刷に示すようにレコードは変更されていません$1
。
$ echo 'one two three' | awk '1 {FS="n" ; OFS=":" ; $1 = $1 ; print $1}'
> one
しかし、私は出力が次のようになりたいと思います。
> o
走りながら記録の再構成を強制するコツは$1 = $1
以下のとおりです。友達マニュアル。だから私はそれがうまくいくことを願っています。何が問題なのかよく分からない。
FS
OFS
単純に設定してから通常のレコードを期待するprint $0
変更されたレコードを印刷してレコードのフィールド区切り文字を変更しようとするのは一般的な間違いです。ただし、レコード自体を変更するために何も実行されないため、これは機能しません。代わりに、通常は
$1 = $1
[...]のような方法でレコードを強制的に書き換える必要があります。
(私はGNU Awk 5.2.2を使用しています)
答え1
~について
特定のレコードのフィールド区切り文字(FS)のみを変更したいと思います。
split()
そのレコードを使用すると、コードがよりクリーンでシンプルになります。
$ 0を書き換えて$ 0を再分割するという2つの概念を混同しています。
$0 再構築:フィールドに値を変更または割り当てると、$ 0がフィールドに書き換えられ、各FSがOFSに置き換えられます。
$ echo 'one two three' |
awk '{FS="n" ; OFS=":" ; $1 = $1 ; print; for (i=1; i<=NF; i++) print i, $i}'
one:two:three
1:one
2:two
3:three
$0 再割り当て:$ 0に値を変更または割り当てると(フィールドの変更により再構築された結果を除く)、$ 0は既存のFS値を使用してフィールドに再分割されます。
$ echo 'one two three' |
awk '{FS="n" ; OFS=":" ; $0 = $0 ; print; for (i=1; i<=NF; i++) print i, $i}'
one two three
1:o
2:e two three
次に、次の結果を理解し、上記の説明を理解したことを確認してください。
再構築してから再分割します。
$ echo 'one two three' |
awk '{FS="n" ; OFS=":" ; $1 = $1 ; $0 = $0; print; for (i=1; i<=NF; i++) print i, $i}'
one:two:three
1:o
2:e:two:three
パーティションを分割して再構築してください。
$ echo 'one two three' |
awk '{FS="n" ; OFS=":" ; $0 = $0; $1 = $1 ; print; for (i=1; i<=NF; i++) print i, $i}'
o:e two three
1:o
2:e two three
答え2
引用したテキストを見てみましょう。
最後に、
awk
sumフィールドの現在の値を使用してレコード全体を強制的に書き換えるのが便利な場合がありますOFS
。
後で次のようになります。
$0
ドメインとの関係には別の側面があります。すべての割り当ての$0
ため、レコードは次のようにフィールドに再解析されます。現在のの価値FS
。
前の文では言及せずにFS
2番目の文で強調した場合、予想される方法は次のとおりです。$0 = $0
反対側ではレコードが変更されます。出力フィールドの値が何であれ、解析を試みずに次のことを行います。
% echo 'one two three' | awk '1 {FS="n" ; OFS=":" ; $0 = $0 ; print $1}'
o
% echo 'one two three' | awk '{FS="n" ; OFS=":" ; $1 = $1 ; print}'
one:two:three
私はGNU awkを使用しません。
% awk --version
awk version 20200816
しかし、私はGNU awkも同じことができたらと思います。