複数のフィールドを含むパイプで区切られたテキストファイルの内容を取得しようとしています。フィールド10はyyyy-MM-dd hh:mm:ss
または形式のタイムスタンプですyyyy-MM-dd hh:mm:ss.SSS
。前者の場合は、フィールドの.'000'
末尾にaを追加したいと思います。それ以外の場合はこれを維持し、他のフィールドは変更せずにそのままにしたいと思います。
私は現在を使用しようとしてawk
いますが、うまくいくようですが、解決策は少し感じます。アッ病棟:-)
awk 'BEGIN {FS=OFS="|"}
{for(i=1;i<9;i++) printf "%s|",$i; printf "%s|",$9}
{printf($10 ~ /\./) ? substr($10,1,10)" "substr($10,12)"|" : substr($10,1,10)" "substr($10,12,18)".000|"}
{for(i=11;i<NF;i++) printf "%s|",$i; printf "%s\n",$NF}'
整理のために私ができることはありますか?
ベストアンサー1
これを「一行」に減らすことが可能でなければなりません。実際に必要なのは、ミリ秒のないタイムスタンプが見つかった場合にフィールド 10 を修正する規則と一般的な場合 (規則 1 による可能な修正を含む) 全体の OK を単に「印刷」する規則です。したがって、次のように仮定しますGNU Awk
。
awk -F'|' -v OFS='|' '$10 ~ /^[[:digit:]]{4}(-[[:digit:]]{2}){2} ([[:digit:]]{2}:){2}[[:digit:]]{2}$/ {$10=$10".000"} {print}' textfile
これで問題が解決します。
ほとんどの場合、上記の正規表現はタイムスタンプを確認するのにとても「完全」です。ファイル形式を十分に信頼している場合は、フィールド10の確認を次のように減らすことができます。
awk -F'|' -v OFS='|' '$10 ~ /:[0-5][0-9]$/ {$10=$10".000"} {print}'
また、GNUバージョンはもう必要ありませんawk
。
テスト入力に適用
a|b|c|d|e|f|i|j|k|2020-01-20 10:22:33|m|n|o
a|b|c|d|e|f|i|j|k|2020-01-20 10:22:33.123|m|n|o
生産する:
~$ awk -F'|' -v OFS='|' '$10 ~ /:[0-5][0-9]$/ {$10=$10".000"} {print}' testinput
a|b|c|d|e|f|i|j|k|2020-01-20 10:22:33.000|m|n|o
a|b|c|d|e|f|i|j|k|2020-01-20 10:22:33.123|m|n|o