bash 外壳脚本。我的脚本中的命令替换问题
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1118601/
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
Shell scripting. Command substitution issue in my script
提问by sourcerebels
On both, my Cygwin and my Linux box (Debian) I'm experiencing same issue:
在我的 Cygwin 和 Linux 机器(Debian)上,我都遇到了同样的问题:
I'm working in a shell script with some kind of formatting ids, I want to add a backslash () before a slash occurrence (/).
我正在使用某种格式 ID 的 shell 脚本,我想在出现斜杠 (/) 之前添加一个反斜杠 ()。
My sed script is working well at my terminal:
我的 sed 脚本在我的终端上运行良好:
# export someid="314-12345/08"
# echo "${someid}" | sed 's/\//\\//'
Output:
输出:
314-12345\/08
But not as well if i run command substitution:
但如果我运行命令替换,情况就不一样了:
# someidformatted=`echo "${someid}" | sed 's/\//\\//'`
sed: -e expression #1, char 9: unknown option to `s'
What I'm missing here?
我在这里缺少什么?
Thank you in advance.
先感谢您。
回答by Grzegorz Oledzki
There's no obligation to use / as the separator for sed.
没有义务使用 / 作为 sed 的分隔符。
s/a/c/
May become
可能会变成
s#a#c#
So in your case:
所以在你的情况下:
someidformatted=`echo "${someid}" | sed 's#\/#\\/#'`
would do the job.
会做的工作。
I can only guess that the problem was caused by some lack of / escaping.
我只能猜测问题是由于缺少/转义引起的。
回答by Ville Laurikari
Here's what is going on. From the bash(1) man page, emphasis mine:
这就是正在发生的事情。从 bash(1) 手册页,强调我的:
When the old-style backquote form of substitution is used, backslash retains its literal meaning except when followed by $, ‘, or \.The first backquote not preceded by a backslash terminates the command substitution. When using the $(command) form, all characters between the parentheses make up the command; none are treated specially.
当使用旧式反引号替换形式时,反斜杠保留其字面意义,除非后跟 $、' 或 \。前面没有反斜杠的第一个反引号终止命令替换。使用$(command)形式时,括号之间的所有字符组成命令;没有被特殊对待。
So most likely you need more backslashes for the command substitution than a plain command.
You can debug this by setting set -x:
因此,与普通命令相比,命令替换很可能需要更多的反斜杠。您可以通过设置来调试set -x:
# someidformatted=`echo "${someid}" | sed 's/\//\\//'`
++ echo 314-12345/08
++ sed 's/\//\//'
sed: 1: "s/\//\//": bad flag in substitute command: '/'
+ someidformatted=
# someidformatted=$(echo "${someid}" | sed 's/\//\\//')
++ echo 314-12345/08
++ sed 's/\//\\//'
+ someidformatted='314-12345\/08'
So, you can see that an occurrence of \\gets turned to \. Adding more backslashes works, but I prefer the $(command)form:
因此,您可以看到出现的\\变成了\。添加更多反斜杠有效,但我更喜欢以下$(command)形式:
# someidformatted=$(echo "${someid}" | sed 's/\//\\//')

