用[a-z],[a-z]替换[a-z],[a-z]并保留字母

时间:2015-06-15 01:01:59

标签: bash awk sed

如何用 [a-z],[a-z] 替换 [a-z],[a-z] 并保留字母?

输入

suny stony brook, stony brook,usa.

输出

suny stony brook, stony brook, usa.

我尝试了什么

sed 's/[a-z],[a-z]/[a-z], [a-z]/g' <<< "suny stony brook, stony brook,usa."
sed 's/[a-z],[a-z]/, /g' <<< "suny stony brook, stony brook,usa."

4 个答案:

答案 0 :(得分:3)

-r用于扩展正则表达式参数
,[^ ] , {}没有&#39} &#39;之后

sed -r 's/,([^ ])/, \1/g' <<< "suny stony brook, stony brook,usa."

获取

suny stony brook, stony brook, usa.

答案 1 :(得分:3)

  

我尝试了什么

sed 's/[a-z],[a-z]/[a-z], [a-z]/g' <<< "suny stony brook, stony brook,usa."

您需要在此处使用正则表达式的捕获组来引用原始的 [a-z] 值。

例如:

s/\([a-z]\),\([a-z]\)/\1, \2/g

请注意我是如何将这些[a-z]\(\)包围的?这些形式捕获组可以稍后通过编写\1\2等来引用(数字表示其位置。)

或者,您可以通过在-r中指定sed开关来启用扩展的正则表达式(例如sed -r),在这种情况下,您只需要编写(和{{ 1}}形成捕获组。

把它放在一起

)

答案 2 :(得分:1)

基于sed的方法有一个问题:

如果两个逗号之间只有一个(小写)字符,则只会用,<space>替换其中一个(第一个)。

e.g。

$ sed -re 's/([a-z]),([a-z])/\1, \2/g' <<<"suny stony brook, stony brook,u,sa."
suny stony brook, stony brook, u,sa.

如果您知道您的输入不包含该角落情况,那么您最好使用sed解决方案。

否则(如果输入可能包含此类数据),则必须使用前瞻/后视 这些在sed中不可用。您必须使用perl

$ perl -ne 's/(?<=[a-z]),(?=[a-z])/, /g; print;' <<< "suny stony brook, stony brook,usa."
suny stony brook, stony brook, usa.

$ perl -ne 's/(?<=[a-z]),(?=[a-z])/, /g; print;' <<< "suny stony brook, stony brook,u,sa."
suny stony brook, stony brook, u, sa.

注意:其他答案/评论中提到的与语言环境相关的警告仍然适用。但他们的解决方案也在这些评论中提供。

答案 3 :(得分:1)

如果您有Gawk,请使用gensub

$ awk '{print gensub(/([[:lower:]]),([[:lower:]])/,"\\1, \\2","g")}' <<<"suny stony brook, stony brook,usa."
suny stony brook, stony brook, usa.