|
パイプ区切り文字()を使用して列4をgrepし、その中のすべての二重引用符を置き換えてから、文字列を二重引用符で囲みます。
サンプルファイル:
col1|col2|col3|col4|col5|col6|col7|col8|col9
value1|value2|value3|"|||||value"4|value5|value6|"||value"7|value8|value9
問題は、4列にユーザーが何でも書くことができるということです。パイプまで書き込むことができます。これは区切り文字であり、これはプロセスを中断します。
たとえば、列 4 は次のようになります。
"|||||value"4
それでは、列4に進み、二重引用符をすべて置き換えてから、二重引用符で囲んでプロセスを機能させるコマンドを作成しようとしています。
列4の出力は次のとおりです。
"|||||value4"
同様に、列7についても同じことを行い、列7に必要な出力は次のとおりです。
"||value7"
最終出力は次のようになります。
col1|col2|col3|col4|col5|col6|col7|col8|col9
value1|value2|value3|"|||||value4"|value5|value6|"||value7"|value8|value9
提案してください。
答え1
使用csvkit
:
$ csvformat -d '|' -D '|' file.csv
col1|col2|col3|col4|col5
test|test_f|21/03/2017|"|||||USER RIGHTa anything here"|123
-d
とフラグは、-D
入力と出力にそれぞれ使用される区切り文字を定義します。
答え2
そしてsed
5つの列のみがあり、そのケースで参照する必要がある列は4列であるとします。
sed -E 's/"//g; s/^(([^|]*\|){3})(.*)(\|[^|]*)$/\1"\3"\4/' infile
ユーザーが引用符を入力しなくても、ユーザーまたはパイプが引用符を入力すると機能します。
これはawk
要求に応じた解決策:
$ awk -F'|' '{ for (i=1; i<NF; i++){if (i>3)gsub("\"","");
printf (i!=(NF-1))?$i"|"((i==3)?"\"":""):$i"\"|"}; print $NF}' infile
col1|col2|col3|"col4"|col5
test|test_f|21/03/2017|"|||||USER RIGHTa anything here"|123