我遇到了这个Hackerrank问题,正则表达式应该匹配HTML标记之间的字符串。正则表达式和字符串是
String str="<h1>Hello World!</h1>";
String regex="<(.+)>([^<]+)</\\1>";
如果'str'具有多个String str="<h1><h1>Hello World!</h1></h1>"
这样的HTML标签,以及([^<]+)
如何捕获此'str'怎么办。
我的问题是([^<]+)
与'str'而不是([a-zA-Z]+)
匹配。
这里是完整的源代码:
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/* Solution assumes we can't have the symbol "<" as text between tags */
public class Solution{
public static void main(String[] args){
Scanner scan = new Scanner(System.in);
int testCases = Integer.parseInt(scan.nextLine());
while (testCases-- > 0) {
String line = scan.nextLine();
boolean matchFound = false;
Pattern r = Pattern.compile(regex);
Matcher m = r.matcher(line);
while (m.find()) {
System.out.println(m.group(2));
matchFound = true;
}
if ( ! matchFound) {
System.out.println("None");
}
}
}
}
别介意我是否愚蠢地问这个问题并预先感谢您!
答案 0 :(得分:2)
如果输入字符串为Hello World!
,则由于感叹号(!)和空格字符,([a-zA-z]+)
将无法正确匹配。
更清楚地说,这是每个正则表达式的含义:
([a-zA-Z]+)
匹配由字母(大写或小写)组成的序列(1个或更多字符)
([^<]+)
匹配一个序列(1个或多个字符),只要一个字符不是一个<字符
答案 1 :(得分:2)
此正则表达式保证您的字符串仅包含一个标签,并假设HTML输入格式正确。
首字母<(.+)>
捕获标签的名称。捕获组还将获得它可以获取的所有属性。由于+
是贪婪的量词,因此它会捕获多个标签。
结尾的</\\1>
与第一个捕获的匹配。这就是为什么如果您的HTML格式正确,则该表达式将无法捕获多个标签或具有以下属性的标签:
<h1>
,结束标签</h1>
✓<h1 attr="value">
,关闭标签</h1>
,但期望</h1 attr="value">
<h1><h2>
,关闭标签</h2></h1>
,但期望</h1><h2>
这就是为什么标签可以与.+
相当安全地匹配的原因,而内容必须与[^<]+
匹配。您想确保您没有抓住内容中的任何停留标签,但完全不允许使用其他任何字符。 [^<]+
(读音。“至少不是<
一次)允许使用!
之类的东西,而[A-za-z]
肯定不允许。