修改引号内的内容BASH

时间:2014-08-05 16:46:42

标签: bash awk sed grep

大家好日子,

我想知道如何修改引号内的内容并保留未经修改的外部。

输入行:

,,,"Investigacion,,, desarrollo",,,

输出行:

,,,"Investigacion, desarrollo",,,

初步尝试:

sed 's/\"",,,""*/,/g' 

但没有任何反应,提前感谢任何线索

4 个答案:

答案 0 :(得分:3)

这种惯用的awk方法很简单:

$ awk 'BEGIN{FS=OFS="\""} {sub(/,+/,",",$2)} 1' file
,,,"Investigacion, desarrollo",,,

或者如果每行可以有多组带引号的字符串:

$ cat file
,,,"Investigacion,,, desarrollo",,,"foo,,,,bar",,,

$ awk 'BEGIN{FS=OFS="\""} {for (i=2;i<=NF;i+=2) sub(/,+/,",",$i)} 1' file
,,,"Investigacion, desarrollo",,,"foo,bar",,,

此方法有效,因为第一个"的所有内容都是字段1,从那里到第二个"的所有内容都是字段2,依此类推,因此" s之间的所有内容都是偶数字段。如果您在字段中有换行符或转义双引号但它会影响其他所有可能的解决方案,它只会失败,所以如果您需要一个处理它的解决方案,您需要将这样的情况添加到示例输入中。

答案 1 :(得分:3)

使用具有内置CSV解析功能的语言(如perl)会有所帮助。

perl -MText::ParseWords -ne '
    print join ",", map { $_ =~ s/,,,/,/; $_ } parse_line(",", 1, $_)
' file
,,,"Investigacion, desarrollo",,,

Text::ParseWords是一个核心模块,因此您无需从CPAN下载它。使用parse_line方法,我们设置分隔符和一个标记以保留引号。然后只需进行简单替换并加入该行即可重新制作CSV。

答案 2 :(得分:2)

使用egrepsedtr

s=',,,"Investigacion,,, desarrollo",,,'
r=$(egrep -o '"[^"]*"|,' <<< "$s"|sed '/^"/s/,\{2,\}/,/g'|tr -d "\n")

echo "$r"
,,,"Investigacion, desarrollo",,,

答案 3 :(得分:1)

使用awk

awk '{ p = ""; while (match($0, /"[^"]*,{2,}[^"]*"/)) { t = substr($0, RSTART, RLENGTH); gsub(/,+/, ",", t); p = p substr($0, 1, RSTART - 1) t; $0 = substr($0, RSTART + RLENGTH); }; $0 = p $0 } 1' 

测试:

$ echo ',,,"Investigacion,,, desarrollo",,,' | awk ...
,,,"Investigacion, desarrollo",,,
$ echo ',,,"Investigacion,,, desarrollo",,,",,, "' | awk ...
,,,"Investigacion, desarrollo",,,", "