首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Javascript regex lookbehind:无效的regexp组

Javascript regex lookbehind:无效的regexp组
EN

Stack Overflow用户
提问于 2020-05-17 05:59:55
回答 4查看 83关注 0票数 2

我有以下使用正则表达式/-+|(?<=: ?).*的小示例。但这会导致Node/Chrome中的无限循环和Firefox中的"Invalig regex group"-error。

当我将其更改为/-+|(?<=: ).*/gm (在后视中省略?-量词)时,它会运行,但是-当然-我不会得到在:之后没有值的行。

如果我将正则表达式更改为/-+|(?<=:).*/gm (将空格留在后面),我将再次运行无限循环/错误。

谁能给我解释一下这种行为,以及我必须使用什么正则表达式才能匹配以冒号结尾的行?我很想理解..。

代码语言:javascript
复制
const text = `
-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------
`;

const pattern = /-+|(?<=: ?).*/gm;

let res;
while((res = pattern.exec(text)) !== null)
{
    console.log(`"${res[0]}"`);
} 

编辑:

预期输出为:

代码语言:javascript
复制
"-------------------------------------"
"5048603"
""
"asjhgg | a3857"
"Something..."
"-------------------------------------"
"5048603"
""
"asjhgg | a3857"
"Something..."
"-------------------------------------"
EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2020-05-17 06:31:02

(?<=...) lookaround是一个正向回溯,在FireFox (参见supported environments here)中还不支持它,因此,在它实现之前,你总是会得到一个异常。

/-+|(?<=: ?).*模式属于可能匹配空字符串的模式,这是一种非常典型的“病态”模式。g标志使JS正则表达式引擎匹配该模式的所有匹配项,为此,它会在有效匹配时推进其lastIndex,但在匹配长度为零的情况下,它不会这样做,而是继续在相同位置再次尝试相同的正则表达式,您最终会陷入循环。请参见how to move here lastIndex,以避免在这些情况下出现无限循环。

在我看来,您希望删除第一个:之前的所有行开头,包括:和之后的所有空格。您可以使用

代码语言:javascript
复制
text.replace(/^[^:\r\n]+:[^\S\r\n]*/gm, '')

或者,如果您想实际提取那些全部是-:之后的行,您可以使用

代码语言:javascript
复制
const text = `
-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------
`;

const pattern = /^-+$|:[^\S\r\n]*(.*)/gm;

let res;
while((res = pattern.exec(text)) !== null)
{
    if (res[1] != undefined) {
      console.log(res[1]);
    } else {
      console.log(res[0]);
    }
}

票数 3
EN

Stack Overflow用户

发布于 2020-05-17 06:09:43

尝试使用此模式:/(.*):(.*)/mg

代码语言:javascript
复制
const regex = /(.*):(.*)/mg;
const str = `-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------
Prop Name: 5048603
Prop2 Name:
Bla bla bla: asjhgg | a3857
Location: Something...
-------------------------------------`;
let m;

while ((m = regex.exec(str)) !== null) {
    // This is necessary to avoid infinite loops with zero-width matches
    if (m.index === regex.lastIndex) {
        regex.lastIndex++;
    }
    
    // The result can be accessed through the `m`-variable.
    m.forEach((match, groupIndex) => {
        console.log(`Found match, group ${groupIndex}: ${match}`);
    });
}

票数 0
EN

Stack Overflow用户

发布于 2020-05-17 06:44:27

首先:Wiktor的答案就是让它跨浏览器工作的答案。

对于任何对如何在Chrome中使用“原始”模式工作感兴趣的人(感谢Wiktor的回答,指出最后一个索引不会在零匹配时递增):

代码语言:javascript
复制
const pattern = /-+|(?<=: ?).*/gm;

let res;
while((res = pattern.exec(text)) !== null)
{
    if(res.index === pattern.lastIndex)
        pattern.lastIndex++;
    console.log(`"${res[0]}"`);
}
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61844157

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档