JS 中的命名组和 OR 运算符

Named groups and OR operator in JS

我正在尝试匹配 2h30m、24h、1d20h30s 等字符串,并使用命名组提取每个片段。听起来简单可行,如果您将 PCRE 与如下正则表达式一起使用:

^(((?<h>[0-9]+)h)|((?<m>[0-9]+)m))+$

regexr上的完整示例,您可以在右上角的 PCRE 和 Javascript 引擎之间切换。

问题是它在 javascript 中不起作用,我不明白为什么。我的猜测是它与 OR 运算符和命名组之间的交互有关,因为在使用 javascript 时,它仅 returns 命名组之一

问题是为什么?如果有任何方法可以在 javascript

中完成这项工作

看来|应该换成?才能连续抓几个组(用|只能抓一行的最后一个组)。并且我们需要添加一个非空断言来防止空字符串匹配。此外,值得插入一些 ?: 以使某些组不捕获。

'use strict';

const str = `
2h30m
24h
1d20h30s
`;

const re = /^(?=.+)(?:(?:(?<d>[0-9]+)d)?(?:(?<h>[0-9]+)h)?(?:(?<m>[0-9]+)m)?(?:(?<s>[0-9]+)s)?(?:(?<ms>[0-9]+)ms)?)+$/gm;

let result;

while (result = re.exec(str)) console.log(result.groups);

如果您的 Node.js(或浏览器)支持新的 matchAll() 方法,也可以通过以下方式实现:

'use strict';

const str = `
2h30m
24h
1d20h30s
`;

const re = /^(?=.+)(?:(?:(?<d>[0-9]+)d)?(?:(?<h>[0-9]+)h)?(?:(?<m>[0-9]+)m)?(?:(?<s>[0-9]+)s)?(?:(?<ms>[0-9]+)ms)?)+$/gm;

console.log(Array.from(str.matchAll(re), ({ groups }) => groups));