Java Matcher.lookingAt 方法
上次修改时间:2025 年 4 月 20 日
Matcher.lookingAt
方法是 Java 正则表达式 API 中的部分匹配操作。它尝试将输入序列的开头与模式进行匹配。与 matches
不同的是,它不需要整个输入都匹配。
如果输入序列的开头与模式匹配,则该方法返回 true
。当您需要检查输入是否以特定模式开头时,它非常有用。该方法不需要整个字符串都匹配。
Matcher.lookingAt 概述
lookingAt
类似于 matches
,但要求更宽松。虽然 matches
要求整个输入都与模式匹配,但 lookingAt
只检查开头。它比 matches
更灵活,但比 find
更严格。
该方法不会更改匹配器的状态。后续调用 lookingAt
将始终从输入的开头开始。它对于验证字符串中的输入前缀或标头很有用。
基本的 lookingAt 示例
此示例演示了 lookingAt
的基本用法。我们检查一个字符串是否以特定模式开头。如果输入的开头符合该模式,则该模式匹配。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtBasic { public static void main(String[] args) { String input = "Hello World!"; Pattern pattern = Pattern.compile("Hello"); Matcher matcher = pattern.matcher(input); boolean result = matcher.lookingAt(); System.out.println("Does input start with 'Hello'? " + result); // Compare with matches() boolean fullMatch = matcher.matches(); System.out.println("Does entire input match 'Hello'? " + fullMatch); } }
在此示例中,lookingAt
返回 true
,因为输入以 "Hello" 开头。但是,matches
返回 false
,因为它要求整个字符串与模式匹配。
使用复杂模式的 lookingAt
lookingAt
与其他匹配方法一样,可以处理复杂的正则表达式模式。此示例演示了如何检查一个字符串是否以有效的日期格式开头。该模式包括数字和特定的分隔符。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtComplex { public static void main(String[] args) { String[] inputs = { "2023-05-15: Meeting at 10am", "15/05/2023: Team lunch", "Invalid date: May 15, 2023" }; Pattern datePattern = Pattern.compile("\\d{4}-\\d{2}-\\d{2}"); for (String input : inputs) { Matcher matcher = datePattern.matcher(input); boolean hasDate = matcher.lookingAt(); System.out.printf("'%s' starts with date? %b%n", input, hasDate); } } }
此代码检查每个字符串是否以 YYYY-MM-DD 格式的日期开头。只有第一个字符串与该模式匹配。如果开头匹配,该方法会忽略日期之后的内容。这对于解析带有标头的结构化文本很有用。
lookingAt vs find vs matches
此示例将 lookingAt
与 find
和 matches
进行比较。每种方法都有不同的匹配行为。理解这些差异对于有效地使用正则表达式至关重要。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtComparison { public static void main(String[] args) { String input = "123 Main Street"; Pattern pattern = Pattern.compile("\\d+"); Matcher matcher = pattern.matcher(input); System.out.println("lookingAt(): " + matcher.lookingAt()); System.out.println("find(): " + matcher.find()); System.out.println("matches(): " + matcher.matches()); // Reset matcher for fresh matching matcher.reset(); System.out.println("\nAfter reset:"); System.out.println("find() from start: " + matcher.find()); System.out.println("Region matches: " + matcher.region(0, 3).matches()); } }
lookingAt
返回 true,因为字符串以数字开头。find
也返回 true,因为它在任何地方找到了数字。matches
失败,因为它要求整个字符串都是数字。区域示例展示了如何将匹配限制到子字符串。
使用组的 lookingAt
lookingAt
支持捕获组,就像其他匹配方法一样。成功匹配后,可以提取组。此示例展示了如何将字符串的开头解析成各个组件。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtGroups { public static void main(String[] args) { String input = "ERROR 2023-05-15: Disk full"; Pattern pattern = Pattern.compile( "(\\w+)\\s(\\d{4}-\\d{2}-\\d{2}):\\s(.*)"); Matcher matcher = pattern.matcher(input); if (matcher.lookingAt()) { System.out.println("Full match: " + matcher.group(0)); System.out.println("Log level: " + matcher.group(1)); System.out.println("Date: " + matcher.group(2)); System.out.println("Message: " + matcher.group(3)); } else { System.out.println("No match found"); } } }
此代码解析日志条目格式。该模式捕获三个组:日志级别、日期和消息。lookingAt
确保整个模式从开头匹配。这些组允许访问匹配的特定部分。
使用多个模式的 lookingAt
此示例展示了如何将 lookingAt
与多个模式一起使用。我们检查哪个模式匹配输入的开头。此技术对于内容类型检测很有用。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtMultiple { public static void main(String[] args) { String input = "<?xml version='1.0'?><root></root>"; Pattern[] patterns = { Pattern.compile("<\\?xml.*\\?>"), // XML declaration Pattern.compile("<html>"), // HTML tag Pattern.compile("\\s*") // Whitespace }; for (Pattern pattern : patterns) { Matcher matcher = pattern.matcher(input); if (matcher.lookingAt()) { System.out.println("Matches: " + pattern.pattern()); break; } } } }
该代码检查哪个模式匹配 XML 字符串的开头。XML 声明模式首先匹配。该方法在第一个成功匹配处停止。这种方法对于格式检测很有效。
使用 Region 的 lookingAt
region
方法限制了 lookingAt
搜索的范围。此示例展示了如何检查输入特定部分的模式。区域对于解析结构化数据很有用。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtRegion { public static void main(String[] args) { String input = "Header: Value\nBody: Content"; Pattern headerPattern = Pattern.compile("Header:"); Pattern bodyPattern = Pattern.compile("Body:"); Matcher matcher = headerPattern.matcher(input); // Check header at start System.out.println("Header at start: " + matcher.lookingAt()); // Set region to after first line matcher.region(input.indexOf('\n') + 1, input.length()); // Check body in region matcher.usePattern(bodyPattern); System.out.println("Body in region: " + matcher.lookingAt()); } }
此代码首先检查字符串开头是否有标头。然后,它设置一个区域到第一个换行符之后,并检查正文模式。区域限制使 lookingAt
仅考虑指定子字符串。
lookingAt 性能考量
此示例演示了 lookingAt
的性能方面。当您只需要检查开头时,该方法可能比 find
更有效。它避免了扫描整个输入。
package com.zetcode; import java.util.regex.Matcher; import java.util.regex.Pattern; public class LookingAtPerformance { public static void main(String[] args) { String longInput = "START " + "x".repeat(1000000); Pattern pattern = Pattern.compile("START"); long startTime = System.nanoTime(); Matcher matcher = pattern.matcher(longInput); boolean result = matcher.lookingAt(); long endTime = System.nanoTime(); System.out.println("lookingAt took: " + (endTime - startTime) + " ns"); startTime = System.nanoTime(); result = pattern.matcher(longInput).find(); endTime = System.nanoTime(); System.out.println("find took: " + (endTime - startTime) + " ns"); } }
对于前缀检查,lookingAt
通常比 find
表现更好。它在检查输入开头后停止。这种差异在大型输入中变得显着。始终为您的需求选择最具体的匹配方法。
来源
在本文中,我们深入探讨了 Matcher.lookingAt
方法。这种部分匹配技术对于许多文本处理任务都很有价值。理解它的行为有助于编写高效而精确的正则表达式代码。
作者
列出所有Java教程。