深入理解正则表达式的预查(Lookahead and Lookbehind)
在正则表达式中,预查(Lookahead and Lookbehind)是一种强大的工具,允许你在不消耗字符的情况下进行匹配检查。预查可以分为四种类型:正向肯定预查、正向否定预查、反向肯定预查和反向否定预查。
1. 正向肯定预查(Positive Lookahead)
概念
正向肯定预查用于确保某个模式出现在当前位置之后,但不会消耗该模式中的字符。语法为 (?=...),其中 ... 是你要查找的模式。
应用场景
当你需要匹配某个模式,且该模式后面必须紧跟另一个特定模式时,可以使用正向肯定预查。
示例
假设我们有一个字符串 "apple pie, banana cake, cherry pie",我们想找到所有以 "pie" 结尾的单词。
const str = "apple pie, banana cake, cherry pie";
const regex = /\b\w+(?= pie)/g;
const matches = str.match(regex);
console.log(matches); // 输出: ["apple", "cherry"]
解释
\b:单词边界。\w+:匹配一个或多个字母数字字符。(?= pie):正向肯定预查,确保当前单词后面紧跟" pie"。
2. 正向否定预查(Negative Lookahead)
概念
正向否定预查用于确保某个模式不在当前位置之后出现,也不会消耗该模式中的字符。语法为 (?!...),其中 ... 是你不希望出现的模式。
应用场景
当你需要匹配某个模式,且该模式后面不能紧跟另一个特定模式时,可以使用正向否定预查。
示例
假设我们有一个字符串 "apple 123, cake 456, banana 789",我们想找到所有不以数字[1-6]为结尾的单词。
const str = "apple 123, cake 456, banana 789";
const regex = /\b[a-z]+\b(?! [1-6]+)/g;
const matches = str.match(regex);
console.log(matches); // 输出: ["banana"]
解释
\b[a-z]+\b:匹配完整的单词。(?! [1-6]+):正向否定预查,确保单词后面不能紧跟数字[1-6]。
3. 反向肯定预查(Positive Lookbehind)
概念
反向肯定预查用于确保某个模式出现在当前位置之前,但不会消耗该模式中的字符。语法为 (?<=...),其中 ... 是你要查找的模式。
应用场景
当你需要匹配某个模式,且该模式前面必须紧跟着另一个特定模式时,可以使用反向肯定预查。
示例
假设我们想找出所有前面跟着 “$” 的数字
const text = "The price is $100 and $200.";
const regex = /(?<=\$)\d+/g;
const matches = text.match(regex);
console.log(matches); // 输出: [ '100', '200' ]
解释
(?<=\$):反向肯定预查,确保数字前面跟着一个$;\d+: 匹配一个或多个数字。
4. 反向否定预查(Negative Lookbehind)
概念
反向否定预查用于确保某个模式不在当前位置之前出现,也不会消耗该模式中的字符。语法为 (?<!...),其中 ... 是你不希望出现的模式。
应用场景
当你需要匹配某个模式,且该模式前面不能紧跟着另一个特定模式时,可以使用反向否定预查。
示例
假设我们想找出所有不前面跟着 “$” 的数字。
const text = "The price is $100 and 200.";
const regex = /(?<!\$)\b\d+/g;
const matches = text.match(regex);
console.log(matches); // 输出: [ '200' ]
解释
(?<!\$):反向否定预查,确保前面没有紧跟"$"。\b\d+: 匹配一个单词边界,然后匹配一个或多个数字。
5.总结
- 正向肯定预查 (
(?=...)):确保当前位置后面紧跟指定模式。 - 正向否定预查 (
(?!...)):确保当前位置后面不紧跟指定模式。 - 反向肯定预查 (
(?<=...)):确保当前位置前面紧跟着指定模式。 - 反向否定预查 (
(?<!...)):确保当前位置前面不紧跟着指定模式。