替换 bash 脚本中两个引号之间的所有逗号
Replace all commas between two quotes in a bash script
我需要在 bash 脚本中将两个 " 之间的所有 "," 替换为 ";"。我很接近了,但是互联网和 Whosebug 上的时间让我想到了这个:
echo ',,Lung,,"Lobular, each.|lungs, right.",false,,,,"organ, left.",,,,,' | sed -r ':a;s/(".*?),(.*?")/;/;ta'
结果:
,,Lung,,"Lobular; each.|lungs; right.";false;;;;"organ; left.",,,,,
正确的是:
,,Lung,,"Lobular; each.|lungs; right.",false,,,,"organ; left.",,,,,
不确定您要如何处理具有奇数个双引号的行(例如,双引号字符串跨越多行),但也许:
awk '!(NR%2){gsub(",",";")} 1' RS=\" ORS=\"
这只是将 "
视为记录分隔符,并且仅对奇数记录进行替换。似乎按预期工作。 (或者,更确切地说,它就像你想要的那样工作!)
正如 oguz 在评论中指出的那样,这会在末尾打印一个额外的 "
。可以通过以下方式解决:
awk '!(NR%2){gsub(",",";")} {printf RFS [=11=]} {RFS="\""}' RS=\"
这有点丑陋但更正确。 (或者更确切地说,不太正确!)如果您的输入流以 "
结尾,该引号将被截断。但是,如果您的输入以换行符而不是 "
终止,这将执行您想要的操作。
OTOH,你可能只想做:
perl -wpE 'BEGIN{$/=}; y/,/;/ if $in; $in = ! $in if $_ eq "\""'
它读取一个字符并使用一个简单的状态机。 ($_
是当前字符,因此 $in = ! $in
会在看到双引号时更改状态,并且音译仅在 $in
为 non-zero 时发生。)
如果你/真的/想要使用 sed
,你可以做整行替换并在现有表达式的开头包含一个像 ^(([^"]*"[^"*]")*[^"]*)
这样的子句,以确保匹配引号是 "odd".
我需要在 bash 脚本中将两个 " 之间的所有 "," 替换为 ";"。我很接近了,但是互联网和 Whosebug 上的时间让我想到了这个:
echo ',,Lung,,"Lobular, each.|lungs, right.",false,,,,"organ, left.",,,,,' | sed -r ':a;s/(".*?),(.*?")/;/;ta'
结果:
,,Lung,,"Lobular; each.|lungs; right.";false;;;;"organ; left.",,,,,
正确的是:
,,Lung,,"Lobular; each.|lungs; right.",false,,,,"organ; left.",,,,,
不确定您要如何处理具有奇数个双引号的行(例如,双引号字符串跨越多行),但也许:
awk '!(NR%2){gsub(",",";")} 1' RS=\" ORS=\"
这只是将 "
视为记录分隔符,并且仅对奇数记录进行替换。似乎按预期工作。 (或者,更确切地说,它就像你想要的那样工作!)
正如 oguz 在评论中指出的那样,这会在末尾打印一个额外的 "
。可以通过以下方式解决:
awk '!(NR%2){gsub(",",";")} {printf RFS [=11=]} {RFS="\""}' RS=\"
这有点丑陋但更正确。 (或者更确切地说,不太正确!)如果您的输入流以 "
结尾,该引号将被截断。但是,如果您的输入以换行符而不是 "
终止,这将执行您想要的操作。
OTOH,你可能只想做:
perl -wpE 'BEGIN{$/=}; y/,/;/ if $in; $in = ! $in if $_ eq "\""'
它读取一个字符并使用一个简单的状态机。 ($_
是当前字符,因此 $in = ! $in
会在看到双引号时更改状态,并且音译仅在 $in
为 non-zero 时发生。)
如果你/真的/想要使用 sed
,你可以做整行替换并在现有表达式的开头包含一个像 ^(([^"]*"[^"*]")*[^"]*)
这样的子句,以确保匹配引号是 "odd".