bash sed 搜索并替换包含 / 的字符串
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/10309968/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
sed search and replace strings containing /
提问by Calvin Cheng
I am having trouble figuring out how to use sed
to search and replace strings containing the /
character in a text file /etc/myconfig
.
我无法弄清楚如何使用sed
来搜索和替换/
文本文件中包含该字符的字符串/etc/myconfig
。
For instance, in my existing text file, I have:
例如,在我现有的文本文件中,我有:
myparam /path/to/a argB=/path/to/B xo
and I want this replaced by:
我希望将其替换为:
myparam /path/to/c argB=/path/to/D xo
I attempted doing this in bash:
我尝试在 bash 中执行此操作:
line='myparam /path/to/a argB=/path/to/B xo'
line_new='myparam /path/to/c argB=/path/to/D xo'
sed -i 's/$line/$line_new/g' /etc/myconfig
But nothing happens.
但什么也没有发生。
Attempting
尝试
grep -rn "$line" /etc/myconfig
does return me 'myparam /path/to/a argB=/path/to/B xo'
though.
'myparam /path/to/a argB=/path/to/B xo'
不过确实让我回来了。
What's the correct way to express my sed
command to execute this search and replace and correctly deal with the /
command? (I reckon that the /
character in my strings are the ones giving me the problem because I used a similar sed
command to search and replace another line in the text file with no problems and that line does not have a /
character.
表达我的sed
命令以执行此搜索并替换和正确处理命令的正确方法是什么/
?(我认为/
我的字符串中的字符是给我带来问题的字符,因为我使用了类似的sed
命令来搜索和替换文本文件中的另一行没有问题,并且该行没有/
字符。
回答by Jonathan Leffler
Don't escape the backslashes; you'll confuse yourself. Use a different symbol after the s
command that doesn't appear in the text (I'm using %
in the example below):
不要逃避反斜杠;你会迷惑自己。在s
未出现在文本中的命令之后使用不同的符号(我%
在下面的示例中使用):
line_old='myparam /path/to/a argB=/path/to/B xo'
line_new='myparam /path/to/c argB=/path/to/D xo'
sed -i "s%$line_old%$line_new%g" /etc/myconfig
Also, enclose the whole string in double quotes; using single quotes means that sed
sees $line
(in the original) instead of the expanded value. Inside single quotes, there is no expansion and there are no metacharacters. If your text can contain almost any plain text character, use a control character (e.g. control-A or control-G) as the delimiter.
另外,用双引号将整个字符串括起来;使用单引号意味着sed
看到$line
(在原始)而不是扩展值。在单引号内,没有扩展,也没有元字符。如果您的文本几乎可以包含任何纯文本字符,请使用控制字符(例如 control-A 或 control-G)作为分隔符。
Note that the use of -i
here mirrors what is in the question, but that assumes the use of GNU sed
. BSD sed
(found on Mac OS X too) requires a suffix. You can use sed -i '' …
to replace in situ; that does not work with GNU sed
. To be portable between the two, use -i.bak
; that will work with both — but gives you a backup file that you'll probably want to delete. Other Unix platforms (e.g. AIX, HP-UX, Solaris) may have variants of sed
that do not support -i
at all. It is not required by the POSIX specification for sed
.
请注意,-i
此处的使用反映了问题中的内容,但前提是使用 GNU sed
。BSD sed
(也可在 Mac OS X 上找到)需要一个后缀。可以使用sed -i '' …
原位更换;这不适用于 GNU sed
。要在两者之间移植,请使用-i.bak
; 这对两者都适用——但会给你一个你可能想要删除的备份文件。其他 Unix 平台(例如 AIX、HP-UX、Solaris)可能具有sed
根本不支持的变体-i
。POSIX 规范不需要它sed
。
回答by potong
This might work for you:
这可能对你有用:
sed -i "s|$line|$line_new|g" /etc/myconfig
You must use "
's so that the $line
and $new_line
are interpolated. Also use |
or any character not found in the match or replacement strings as a delimiter.
您必须使用"
的,以便$line
和$new_line
插值。还可以使用|
或 在匹配或替换字符串中找不到的任何字符作为分隔符。