
だから私がやろうとしていることは次のとおりです。サンプルCSVを見る:
1,3917,3917,BGP=694|Ethernet=1610|LAG=3,Y
スクリプトを実行した後、出力は次のようになります。
1,3917,3917,BGP=694,Y
1,3917,3917,Ethernet=1610,Y
1,3917,3917,LAG=3,Y
追加の区切り文字を含む元のCSVファイルの1行は、4行目に3つの追加フィールドがあるため、3行に変換されます。
私は一日中これについて研究してきた、これが私が思いついたものです。動作しますか?
パスワード:
#!/usr/bin/ksh
if [ $# -ne 1 ];
then echo "Usage: read.sh filename";
exit 1;
fi
file="$1"
while read line
do
IFS='|'
set x $line
while [ a -le #$]
do
a=a+1
echo "`$1`,`$a`"
done
done < $1
答え1
代わりにAWKを使用してください
この問題は、AWKを使用すると、はるかに簡単に解決できます。私はこれをGNU AWKでテストしました。他のものを使用する場合は、少し調整する必要があります。
#!/usr/bin/gawk -f
BEGIN { FS = "|" }
{
split( $3, array, /,/ )
print $1 "," array[2]
print $1 "," $2 "," array[2]
print $1 "," $3
}
スクリプトをどこかに保存します(例:解析.awk)実行可能であることを確認してください。その後、CSVファイルまたは標準入力からスクリプトを呼び出して、次の結果を収集できます。
$ echo '1,3917,3917,BGP=694|Ethernet=1610|LAG=3,Y' | parse.awk
1,3917,3917,BGP=694,Y
1,3917,3917,BGP=694,Ethernet=1610,Y
1,3917,3917,BGP=694,LAG=3,Y
答え2
あなたが持っているのは、パイプ記号で区切られたグループ化された値を含むフィールドのようです。
あなたはそれを使用することができますミラー(mlr
)これらのグループ化された値を別の新しいレコードに「爆発」します。
$ mlr --csv -N nest --evar pipe -f 4 file
1,3917,3917,BGP=694,Y
1,3917,3917,Ethernet=1610,Y
1,3917,3917,LAG=3,Y
file
これは、ヘッダーなしのCSVファイルから入力を読み取り、次にnest
4番目のフィールドのパイプで区切られたサブフィールドを新しいレコードに分割する操作を適用します。
逆の操作を実行することもできます。つまり、4番目のフィールドの値をパイプで区切られた結合フィールドに「埋め込む」こともできます。
$ cat file
1,3917,3917,BGP=694,Y
1,3917,3917,Ethernet=1610,Y
1,3917,3917,LAG=3,Y
$ mlr --csv -N nest --ivar pipe -f 4 file
1,3917,3917,BGP=694|Ethernet=1610|LAG=3,Y
MillerはCSVをサポートしているため、カンマや改行を含むフィールドを含むデータには問題はありません。