此答案中使用的术语:
-
Match 表示针对字符串运行 RegEx 模式的结果,如下所示:
someString.match(regexPattern)。
-
匹配模式表示输入字符串的所有匹配部分,它们都位于 match 数组中。这些都是输入字符串中模式的所有实例。
-
匹配组表示要捕获的所有组,在 RegEx 模式中定义。 (括号内的模式,如下所示:
/format_(.*?)/g,其中(.*?) 将是一个匹配组。)它们位于匹配模式中。
说明
要访问匹配的组,在每个匹配的模式中,您需要一个函数或类似的东西来迭代匹配。正如许多其他答案所示,有多种方法可以做到这一点。大多数其他答案使用 while 循环来迭代所有 匹配的模式,但我认为我们都知道这种方法的潜在危险。有必要匹配 new RegExp() 而不仅仅是模式本身,它只在评论中提到。这是因为 .exec() 方法的行为类似于 生成器函数 – it stops every time there is a match,但会保留其 .lastIndex 以在下一次 .exec() 调用时从那里继续。
代码示例
下面是函数searchString 的示例,它返回所有匹配模式的Array,其中每个match 是一个Array,其中包含所有匹配组。我没有使用 while 循环,而是提供了使用 Array.prototype.map() 函数的示例以及更高效的方式 - 使用普通的 for-loop。
简洁的版本(更少的代码,更多的语法糖)
这些性能较差,因为它们基本上实现了forEach-loop,而不是更快的for-loop。
// Concise ES6/ES2015 syntax
const searchString =
(string, pattern) =>
string
.match(new RegExp(pattern.source, pattern.flags))
.map(match =>
new RegExp(pattern.source, pattern.flags)
.exec(match));
// Or if you will, with ES5 syntax
function searchString(string, pattern) {
return string
.match(new RegExp(pattern.source, pattern.flags))
.map(match =>
new RegExp(pattern.source, pattern.flags)
.exec(match));
}
let string = "something format_abc",
pattern = /(?:^|\s)format_(.*?)(?:\s|$)/;
let result = searchString(string, pattern);
// [[" format_abc", "abc"], null]
// The trailing `null` disappears if you add the `global` flag
高性能版本(更多代码,更少语法糖)
// Performant ES6/ES2015 syntax
const searchString = (string, pattern) => {
let result = [];
const matches = string.match(new RegExp(pattern.source, pattern.flags));
for (let i = 0; i < matches.length; i++) {
result.push(new RegExp(pattern.source, pattern.flags).exec(matches[i]));
}
return result;
};
// Same thing, but with ES5 syntax
function searchString(string, pattern) {
var result = [];
var matches = string.match(new RegExp(pattern.source, pattern.flags));
for (var i = 0; i < matches.length; i++) {
result.push(new RegExp(pattern.source, pattern.flags).exec(matches[i]));
}
return result;
}
let string = "something format_abc",
pattern = /(?:^|\s)format_(.*?)(?:\s|$)/;
let result = searchString(string, pattern);
// [[" format_abc", "abc"], null]
// The trailing `null` disappears if you add the `global` flag
我尚未将这些替代方案与之前在其他答案中提到的替代方案进行比较,但我怀疑这种方法的性能和故障安全性都低于其他方法。