我有一个需要验证的正则表达式。正则表达式中有双引号,但我似乎无法弄清楚如何正确地逃避它们。
首次尝试,不起作用,因为报价未被转义。
while read line
do
if [[ $line =~ "<a href="(.+)">HTTP</a>" ]]; then
SOURCE=${BASH_REMATCH[1]}
break
fi
done < tmp/source.html
echo "{$SOURCE}" #output = {"link.html"} (with double quotes)
如何正确运行此输出,输出为 link.html ,不带双引号。
我试过......
while read line
do
if [[ $line =~ "<a href=/"(.+)/">HTTP</a>" ]]; then
SOURCE=${BASH_REMATCH[1]}
break
fi
done < tmp/source.html
echo "{$SOURCE}" #output = {}
没有运气。有人可以帮助我,这样我就可以不再在我的桌子上敲打头了吗?我对Bash不太满意。谢谢!
答案 0 :(得分:10)
将你的正则表达式放在一个变量中总是最好的。
pattern='<a href="(.+)">HTTP</a>'
while read line
do
if [[ $line =~ $pattern ]]; then
SOURCE=${BASH_REMATCH[1]}
break
fi
done < tmp/source.html
echo "{$SOURCE}" #output = {link.html} (without double quotes)
如果引用右侧(模式),它会将匹配从正则表达式更改为等于的简单字符串(=~
实际上变为==
)。
作为旁注,转义是使用反斜杠(\
)而不是斜杠(/
)完成的,但由于前一段中提到的外部引号,这对您的情况没有帮助。
答案 1 :(得分:2)
$line =~ "<a href=\"(.+)\">HTTP</a>"
答案 2 :(得分:1)
我建议在指定正则表达式时始终使用变量:
#!/bin/bash
SOURCE=
url_re='<a href="(.+)">HTTP</a>'
while read line
do
if [[ "$line" =~ $url_re ]]; then
SOURCE=${BASH_REMATCH[1]}
break
fi
done < test.txt
echo $SOURCE # http://example.com/
# test.txt contents:
# <a href="http://example.com/">HTTP</a>
答案 3 :(得分:0)
试试这个"<a href="""(.+)""">HTTP</a>"
编辑,试试这个
"<a href="\""(.+)"\"">HTTP</a>"
或
'<a href="(.+)">HTTP</a>'
或
'<a href='\"'(.+)'\"'>HTTP</a>'
&lt; - 这将在Bash中提供正确的语法,就像正则表达式(。+)一样,不知道它将如何发挥
编辑,当你使用这个正则表达式"<a href=(.+)>HTTP</a>"
??
答案 4 :(得分:0)
没有中间变量(即,直接在=〜之后使用正则表达式),仅当正则表达式模式没有某些字符(空格,<或>等)并且您删除了正则表达式周围的引号时,它才有效或正则表达式为纯字母数字字符串
$ x='Hello'
$ [[ $x =~ ^H ]] && echo OK
OK
$ [[ $x =~ 'H' ]] && echo OK
OK
$ [[ $x =~ H ]] && echo OK
OK
我偶然发现了有关bash设计的解释,而该解释通常不允许您在=〜之后直接使用regex。例如
$ re='^H'
$ [[ $x =~ $re ]] && echo OK
OK
按预期运行,而
$ [[ $x =~ '^H' ]] && echo OK
没有。我个人总是将正则表达式放在变量的首位。但是我仍然想知道为什么bash是这样设计的。您可以争辩说首先将正则表达式分配给变量将使代码看起来更整洁。还有其他原因吗?如果不应该将正则表达式解释为字符串,则bash可以使用其他方式来表示它。例如,Perl使用斜杠,/ regex /,或更明确地使用m / regex/。