这两个正则表达式有什么作用?
/<(.*?)>.*?<\/\1>/
/<(.*?)>.*<\/\1>/
我所学到的是.*?
意味着尽可能少的角色。
例如:
my $a = '"helllo"++"world"';
print "a $1\n" if $a =~/(".*")/; # "helllo"++"world"
print "b $1\n" if $a =~/(".*?")/; # "helllo"
print "c $1\n" if $a =~/(.*)/; # "helllo"++"world"
print "d $1\n" if $a =~/(.*?)/; # (nothing)
为什么d什么都不显示,b是helllo
而不是""
?
所以,我找不到任何好的例子来显示1 and 2
与helllo world
示例之间的区别。
有人可以举一些例子来说明差异吗?
感谢。
答案 0 :(得分:1)
*
表示匹配零次或多次
*?
表示匹配零次或多次但不贪心
.
表示它匹配除新行
'"helllo"++"world"'
这是你的骚动
在下面的示例中,^
表示当前位置(字符串中有当前位置,模式中有当前位置(种类))
在你的第一个案例中。
步骤1
"helllo"++"world" ".+"
^ ^
第二步
"helllo"++"world" ".+"
^ ^
步骤3
"helllo"++"world" ".+"
^ ^
步骤4
由于我们在字符串"
回溯的末尾找到.+
并匹配"
检查"
We have the match at this position so success
"helllo"++"world" ".+"
^ ^
在你的第二个案例中。 *? Match zero or more times but not greedy
步骤1
"helllo"++"world" ".*?"
^ ^
第二步
"helllo"++"world" ".*?"
^ ^
步骤3
"helllo"++"world" ".*?"
^ ^
Step4(*
在第一场比赛满足时失败。)
"helllo"++"world" ".*?"
^ ^
在你的第三种情况下
第1步
"helllo"++"world" .*
^ ^
第2步(*
贪婪,直到结束。结果是给出所有匹配的模式)
"helllo"++"world" .*
^ ^
在你的第四个案例中,
您的模式为.*?
这意味着(.)
零或更多次(*)
,但不是贪婪(?)
。这里非贪婪的字符与零字符匹配,因此结果为空。
答案 1 :(得分:1)
.*?
将使用尽可能少的字符搜索匹配项。如果您将".*?"
与"a" "b"
匹配,则正则表达式引擎将仅报告"a"
作为匹配项。贪婪版本".*"
会将整个字符串报告为匹配项,因为*
希望尽可能多地使用输入。
正则表达式.*?
可以满足一个空字符串,所以如果你不在它周围放任何东西,以防止匹配正是它所做的事情(比如你的情况d)。
你的正则表达式1)和2)用于解析看起来像XML的文本。请考虑以下文字:
<tag>text</tag> <tag>more text</tag>
正则表达式1)将仅消耗第一个带标记的子字符串<tag>text</tag>
,而正则表达式2消耗整个字符串。
现在考虑一下这个文字:
<tag>what about <tag>nested</tag> tags?</tag>
正则表达式1)只会产生匹配,直到第一个结束</tag>
,而正则表达式2)消耗整个字符串。
答案 2 :(得分:1)
你真的有两个问题,一个在这里;
这两个正则表达式有什么作用?
/≤(?*)&GT。* LT; / \ 1&GT; /
点,&#39;。&#39;,是匹配任何字符的原子。后面的星号表示&#34;尽可能多地匹配前一个原子。&#34;这种组合被称为&#34;贪婪&#34;因为点匹配任何东西和&#39; *&#39;说 - &#34;继续前进&#34;因此,在没有任何其他约束或锚点的情况下,组合使用&#39;吃或匹配字符串的其余部分。问号会改变这种行为来自&#34;贪婪&#34;到&#34;吝啬&#34; - 它会尽可能少地匹配。
圆括号 - 或括号 - 没有规定要匹配的内容 - 它们表示你想要捕获&#34;与名为&#34; $ 1&#34;的特殊变量匹配的任何内容对于第一对括号,&#34; $ 2&#34;对于第二个等等。
所以这个, - <(.*?)>
意味着,匹配一个开放的尖括号(或者#34;小于&#34;),然后匹配任何东西(但是尽可能少地占用),然后匹配一个闭合角度(或&#34;大于&#34;)。圆括号没有规定什么匹配 - 它们只是意味着&#34;将尖括号之间的任何文本放入$ 1。&#34;
最后一部分中的\1
,<\/\1>
,被称为后引用 - 它意味着&#34;无论你在第一组圆括号中捕获了什么,我想要再次在这里匹配&#34;。它之前的\/
是一个转义正斜杠 - 所以我们在这里寻找的是一个&#34;标签&#34; (由尖括号括起来的文字),一些文字然后匹配的&#34;结束标记&#34; - 即尖括号中的相同文字带有&#39; /&#39;在前面。
/≤(?*)&GT。* LT; / \ 1&GT; /
除了尝试在开始标记和结束标记之间尽可能多地使用文本之外,这几乎完全相同。
my $a = '"helllo"++"world"';
...
print "b $1\n" if $a =~/(".*?")/; # "helllo"
...
print "d $1\n" if $a =~/(.*?)/;
为什么d什么都不显示,b是&#34; helllo&#34;不是&#34;&#34;?
用(b),你说&#34;我在开始时坚持双引号(&#34;),然后是任何文字,然后我再次坚持收尾双引号(&#34; )&#34 ;.现在,如果您查看$ a中的文本,您可以看到以下所有内容的开头和结尾(&#34;),其中包含一些文本;
"helllo"
"helllo"++"
"helllo"++"world"
这里的主要观点 - .*?
(吝啬)意味着&#34;我想要最小的一个&#34; - 即在这种情况下是第一个,而.*
(没有&#39;?&#39; - 贪婪)意味着&#34;我想要最长的一个&#34; - 即在这种情况下,最后一个。
使用(d),你没有在字符串的开头或结尾处规定的尖括号或双引号字符 - 你只是说&#34;匹配任何东西,(。*)但尽量少用& #34 ;.因此,RE根本没有给你什么,因为它肯定是满足标准的最小匹配(即没有标准!: - )
答案 3 :(得分:0)
原因d)打印没有什么是非常简单的:你已经知道.*?
匹配尽可能少,所以没有添加任何其他标准,“尽可能少”根本就没有。
b)"(.*?)"
匹配"hello"
的原因是表达式中的两个引号 - 即匹配(如果找到)必须以引号开头和结尾。中间部分.*?
匹配尽可能少,所以这是“你好”。