awkで末尾のカンマを避けながら出力レコードを ','で区切る方法

awkで末尾のカンマを避けながら出力レコードを ','で区切る方法

次のawk文とその出力を考慮してください。

$ awk -F "/" '/\/tcp/ {print $1}' input_file

10\n
20\n

私が望む出力は次のとおりです。

10,20

私が試したことは次のとおりです。

$ awk -F "/" 'BEGIN{ORS=","} /\/tcp/ {print $1}' input_file
10,20,

最後にカンマを削除する方法は?

答え1

ORSをに設定しないでください。,これはスクリプトの出力が改行で終わらないため、POSIXでは有効なテキストファイルではないため、それを使用して呼び出す他のスクリプトと同じことを行います。代わりに、プラットフォームが持っている必要があるすべての値を保持するようにORSをそのままにして、,出力したいすべての文字列の前に最初の文字列を除くすべての文字列を印刷します。

awk -F '/' '/\/tcp/{printf "%s%s", sep, $1; sep=","} END{print ""}'

たとえば、

$ seq 3 | awk '{printf "%s%s", sep, $0; sep=","} END{print ""}'
1,2,3

答え2

個人的には、印刷後にカンマを削除します。

awk -F "/" 'BEGIN{ORS=","}/\/tcp/ {print $1}' | sed 's/,$//'

または末尾の改行を追加してください。

awk -F "/" 'BEGIN{ORS=","}/\/tcp/ {print $1}' | sed 's/,$/\n/'

本当にこれを行うには、ややawkエレガントではない次のアプローチを試してみてください。

awk -F "/" '/\/tcp/{ if(NR == 1){ printf "%s", $1} else{ printf ",%s",$1}}'

そして、末尾の改行を追加するには:

awk -F "/" '/\/tcp/{ if(NR == 1){ printf "%s", $1} else{ printf ",%s",$1}}END{print ""}'

答え3

無応答は、awk質問が説明されているように単純であると仮定します。

paste -s -d',' input_file

-s, --serialファイルが順次処理されることを示します(paste通常は複数のファイルの行をマージするために使用されます)。

-d, --delimiters区切り記号の指定(デフォルトはタブ)

答え4

あなたがやっていることは、収集されたデータの複数の行に基づいて単一の出力レコードを構築することです。それではこれをやってみましょう:

awk -F '/' '
    BEGIN { OFS = "," }
    /\/tcp/ { a[++n] = $1 }
    END {
        $0 = ""
        for (i = 1; i <= n; ++i)
            $i = a[i]
        print
    }' input_file

これはデータを配列として収集し、aそのEND配列のフィールドを使用してブロックに新しいレコードを作成します。存在する非常に最後に履歴を印刷します。OFSブロックにコンマを設定するので、フィールドはコンマで区切られますBEGIN

テスト:

$ awk -F '/' 'BEGIN {OFS=","} /\/tcp/ {a[++n]=$1} END {$0="";for (i=1;i<=n;++i) $i = a[i];print}' <<END_INPUT
first/tcp
no relevant
second/tcp
third/tcp
END_INPUT
first,second,third

(上記の最後の行は出力であり、入力はここで区切られた文書を介して提供されますEND_INPUT。)

関連情報