web-dev-qa-db-ja.com

一致した正規表現に接尾辞を追加します

最初のフィールドに数字を含む行がいくつかあります。

46066.874.89
48569.123.56
56489.256.88
654.12.32
84689.25.69

ここで実行したいのは、4行目の00の最後に654を追加し、ファイル内の最初の.の前に3つの数字が出現するたびに追加することです。どうすればいいですか?使ってみました

sed 's/^[0-9][0-9][0-9]./&00/'

しかし、私が得る出力は

4606006.874.89
4856009.123.56
5648009.256.88
654.0012.32
8468009.25.69
2
Johnny

もうすぐです:

$ sed -E 's/^([0-9][0-9][0-9])\./\100./' file 
46066.874.89
48569.123.56
56489.256.88
65400.12.32
84689.25.69
3
terdon

sedコマンドは、3桁の後に2つのゼロを挿入し、すべての行の先頭に別の文字を挿入します。 _._は「任意の文字」に一致します。実際のドットと一致するようにドットを_\._としてエスケープした場合でも、2つのゼロafterドットを挿入したことになります。

少し調整すると機能します。

_$ sed 's/^\([0-9]\{3\}\)\./\100./' file
46066.874.89
48569.123.56
56489.256.88
65400.12.32
84689.25.69
_

または、sedが拡張正規表現をサポートしている場合(最近はほとんどがサポートされています):

_$ sed -E 's/^([0-9]{3})\./\100./' file
46066.874.89
48569.123.56
56489.256.88
65400.12.32
84689.25.69
_

awkを使用して、もう少し一般的にします。

_$ awk -F . 'BEGIN { OFS=FS } length($1) < 5 { $1 = sprintf("%s%.*d", $1, 5 - length($1), 0) }; 1' file
46066.874.89
48569.123.56
56489.256.88
65400.12.32
84689.25.69
_

このawkコマンドは、ドットで区切られた最初の列の5文字未満のエントリごとに、文字列の全長が5文字になるように、必要な数のゼロを文字列に入力します。

これは、整数_0_をゼロで埋められた文字列として不足している長さにフォーマットすることによって行われます。次に、これはフィールド内の既存のデータと連結されます。

これは、最初のフィールドの短い文字列(3文字を含む文字列だけでなく)に対して機能します。

文字列の先頭にゼロを入力する方が簡単です(ただし、要求されたものではなく、許可されています)。

_$ awk -F . 'BEGIN { OFS=FS } { $1 = sprintf("%.5d", $1) }; 1' file
46066.874.89
48569.123.56
56489.256.88
00654.12.32
84689.25.69
_

最初のフィールドに整数が含まれているという事実を使用して、正しい幅のゼロで埋められた整数としてsprintf()でフォーマットします。

どちらのコマンドでも、最後の_1_は、現在の行を出力するデフォルトのアクションを呼び出します(_{ print }_または_{ print $0 }_に置き換えることができます)。

1
Kusalananda