我需要在一个小的bash脚本中替换一个文件中的字符串但是...我得到了奇怪的结果。
假设我要替换:
<tag><![CDATA[text]]></tag>
使用:
<tag><![CDATA[replaced_text]]></tag>
我应该使用sed
吗?我认为由于/
和[
]
我得到了奇怪的结果......
接近这个的最佳方式是什么?
答案 0 :(得分:4)
带-p选项的Perl几乎和sed一样工作,它的正则表达式有\ Q(quote)开关:
perl -pe 's{\Q<tag><![CDATA[text]]></tag>}
{<tag><![CDATA[replaced_text]]></tag>}' YOUR_FILE
在Perl中,您可以使用不同的标点符号来分隔表达式(在我的示例中为{...} {...}。)
答案 1 :(得分:3)
是的,您需要转义括号,并使用转义斜杠或使用不同的分隔符。
sed 's,<tag><!\[CDATA\[text\]\]></tag>,<tag><!\[CDATA\[replaced)text\]\]></tag>,'
也就是说,在使用正则表达式时,SGML和XML实际上并不比HTML更好;不要指望这个概括。
答案 2 :(得分:0)
这应该足够了:
$ echo '<tag><![CDATA[text]]></tag>' | sed 's/\[text\]/\[replaced_text\]/'
<tag><![CDATA[replaced_text]]></tag>
您还可以将sed内的/
分隔符更改为其他字符,例如,
,|
或%
。
答案 3 :(得分:0)
只需使用除/之外的分隔符,这里我使用#:
sed -i 's#<tag><!\[CDATA\[text\]\]></tag>#<tag><![CDATA[replaced_text]]></tag>#g' filename
-i
让sed更改文件而不是将其打印出来。
g
用于匹配多次(全局)。
但是你知道你想要匹配的确切字符串,包括标签和文本吗? 例如,如果您想用replace_text替换所有文本:
perl -i -pe 's#(<tag><!\[CDATA\[)(.*?)(\]\]></tag>)#\1replaced_text\3#g' filename
切换到perl,因为sed不支持非贪婪的乘数(*?)。