正则表达式在Java中不正确匹配

正则表达式在Java中不正确匹配,java,regex,Java,Regex,我编写了一个程序来查找HTML页面中的所有链接: public static void main(String[] args) throws IOException { String base = "http://www.oracle.com/"; URL url = new URL(base); BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream())); St

我编写了一个程序来查找HTML页面中的所有链接:

public static void main(String[] args) throws IOException {
    String base = "http://www.oracle.com/";
    URL url = new URL(base);
    BufferedReader in = new BufferedReader(new InputStreamReader(url.openStream()));

    StringBuffer stringBuffer = new StringBuffer();
    String inputLine = null;
    while ((inputLine = in.readLine()) != null) {
        stringBuffer = stringBuffer.append(inputLine).append("\n");
    }

    Matcher matcher = Pattern.compile("<a .*href=\"([^\"]+)\".*</a>", Pattern.DOTALL).matcher(stringBuffer.toString());

    ArrayList<String> urlList = new ArrayList<>();
    while (matcher.find()){
        String relUrl = matcher.group(1);
        String fullUrl = relUrl.startsWith("/")?base+relUrl.substring(1):relUrl;
        urlList.add(fullUrl);
        System.out.println(fullUrl);
    }

    in.close();
}

根据,正则表达式
,因为正则表达式中的正则表达式是贪婪的
*
,所以正则表达式匹配所有字符。所以,让它成为非贪婪的
*?

"<a .*?href=\"([^\"]+)\".*?</a>"
“”

Regex不应用于非规则结构的输入。这就是解析器(比如HTML解析器)的用途。我理解,但HTML解析器不是我的选择(这是一门课程的挑战性作业,要求我们使用正则表达式),它可以工作,谢谢。出于好奇,为什么没有
DOTALL
标志,模式可以匹配100个左右的链接?我认为
DOTALL
标志不会影响模式的贪婪性?因为一行上存在100个锚定标记。是的,但是为什么对于这100个标记,
*
与所有字符都不匹配?可能是因为\n字符之间存在。我还是不明白你的意思。发布一个示例数据和您在regex101上尝试的regex。然后把链接还给我。@SimonZhu
DOTALL
并不影响贪婪,但它实际上允许
*
中的点匹配换行符。因此,
*
将消耗整个页面,直到最后出现
href=…
"<a .*?href=\"([^\"]+)\".*?</a>"
"<a [^<>]*\\bhref=\"([^\"]+)\".*?</a>"