我有一个包含大量下划线的文件,我必须用空字符串替换它们,除了那些属于特定字符串usr_mstr的字符串。 我尝试过sed命令,它取代了下划线并排除了我提供的单词,但它也在紧跟下划线后替换了该字符!任何帮助将不胜感激..
echo "fname_sname_id_usr_mstr" | sed 's/_[^usr_mstr]//g'
预期产出:
fnamesnameidusr_mstr
实际输出:
fnamenamedusr_mstr
(s
和i
已被替换)
答案 0 :(得分:6)
这可能适合你(GNU sed):
sed -r 's/(usr_mstr)|_/\1/g' file
全局替换usr_mstr
或自行替换_
答案 1 :(得分:5)
[^usr_mstr]
是一个字符类,匹配任何不是u
,s
,r
,m
,t
或{的字符。 {1}}。
Perl支持“环顾”断言,所以你可以写:
_
即。如果之前没有echo "fname_sname_id_usr_mstr_x_usr_other_mstr_y_usrmstr_z" \
| perl -pe 's/(?<!usr)_//g;s/_(?!mstr)//g'
,则替换_,而不是usr
。
答案 2 :(得分:0)
单独使用标准sed BRE正则表达式无法解决这个问题。使用sed
,您基本上需要替换&#34; usr_mstr&#34;使用占位符字符串,然后替换所有下划线,然后用&#34; usr_master&#34;替换占位符字符串。 ..
echo "fname_sname_id_usr_mstr" |
{ null="@#@"; sed "s/usr_mstr/$null/g; s/_//g; s/$null/usr_mstr/g" ;}
另一种方法是尝试awk:
echo "fname_sname_id_usr_mstr" |
awk -v s="usr_mstr" 'BEGIN{FS=OFS=s} {for(i=1; i<=NF; i++) gsub("_","",$i)}1'
只要s
不包含扩展正则表达式中特殊的常规字符,哪个应该有效。