439. Java 正则表达式 - 字符串字面量与元字符
1. 字符串字面量匹配(String Literals)
正则表达式最基础的功能就是 匹配一个固定的字符串。
👉 如果正则表达式是 "foo",输入字符串也是 "foo",匹配就会成功。
🌰 示例
public static void main(String[] args) {
java.util.Scanner scanner = new java.util.Scanner(System.in);
System.out.println("\n=== 正则表达式交互式测试 ===");
System.out.println("提示: 输入 'quit' 退出程序\n");
while (true) {
System.out.print("Enter your regex: ");
String regexInput = scanner.nextLine();
if ("quit".equalsIgnoreCase(regexInput)) {
System.out.println("程序已退出");
break;
}
try {
Pattern userPattern = Pattern.compile(regexInput);
System.out.print("Enter input string to search: ");
String inputString = scanner.nextLine();
Matcher userMatcher = userPattern.matcher(inputString);
boolean found = false;
while (userMatcher.find()) {
found = true;
System.out.printf("I found the text \"%s\" starting at index %d and ending at index %d.%n",
userMatcher.group(), userMatcher.start(), userMatcher.end());
}
if (!found) {
System.out.println("No match found.");
}
} catch (Exception e) {
System.out.println("正则表达式错误: " + e.getMessage());
}
System.out.println(); // 空行分隔
}
scanner.close();
}
Enter your regex: foo
Enter input string to search: foo
I found the text foo starting at index 0 and ending at index 3.
这里有几个细节:
- 输入
"foo"长度是 3,但结果显示:- start index = 0
- end index = 3
- 为什么?因为正则里的索引范围是:
- 起始索引 inclusive(包含)
- 结束索引 exclusive(不包含)
👉 用一个图来帮助理解:
String: f o o
Index: 0 1 2 3
"foo"实际占用的是 0, 1, 2 三个单元格- 但结束索引指向 3(相当于最后一个字符的“后面”)
🌰 连续匹配的例子
Enter your regex: foo
Enter input string to search: foofoofoo
I found the text foo starting at index 0 and ending at index 3.
I found the text foo starting at index 3 and ending at index 6.
I found the text foo starting at index 6 and ending at index 9.
👉 可以看到,下一个匹配的开始位置就是上一个匹配的结束位置。这就是正则引擎的匹配机制。
2. 元字符(Metacharacters)
正则表达式并不仅仅是匹配固定字符串,它有一组 特殊字符(metacharacters),能让匹配变得更灵活。
🌰 示例:.(点号)
如果正则表达式是 "cat.",输入字符串是 "cats",结果如下:
Enter your regex: cat.
Enter input string to search: cats
I found the text cats starting at index 0 and ending at index 4.
👉 注意:虽然输入中没有写 .,但匹配依然成功。
原因是:. 是一个元字符,表示 任意单个字符。
所以 "cat." 可以匹配:
"cats""cata""cat!""cat?"等等。
Java 正则里的元字符列表
<([{\^-=$!|]})?*+.>
这些符号在正则表达式里都有特殊含义。
👉 但注意:像 @、# 这样的符号永远没有特殊含义,始终是普通字符。
3. 如何匹配“普通的元字符”
有时我们并不想让 . 当作“任意字符”,而是就想匹配一个真正的点号 "."。
👉 这时有两种方式:
-
用反斜杠
\转义Pattern p = Pattern.compile("cat\\."); Matcher m = p.matcher("This is a cat."); System.out.println(m.find()); // true"cat\\."表示 匹配字面量字符串 "cat."- 之所以要写两个
\\,是因为在 Java 字符串里\也需要转义。
-
用
\Q...\E引用区块Pattern p = Pattern.compile("\\Qcat.\\E"); Matcher m = p.matcher("This is a cat."); System.out.println(m.find()); // true\Q开始转义,直到\E结束。- 中间的所有字符都会被当作普通字符。
- 所以
"\\Qcat.\\E"等价于"cat\\."。
4. 小结 ✅
- 字符串字面量:正则
"foo"匹配输入"foo" - 索引规则:开始索引包含,结束索引不包含
- 元字符:
.表示任意单字符 - 转义方法:
- 用
\\转义(常见方式) - 用
\Q...\E包裹
- 用
🎤QA
- 让学员尝试写出一个能匹配
"1+1=2"的正则(需要转义+和=) - 提问:
".*"能匹配什么内容? - 提问:
"foo."和"foo\\."有什么区别?