使用Node.js和正确的正则表达式,我需要匹配任何=
,其后应是无空格的任何字符串,然后是可以包含空格的任何字符串。
我有一个看起来像这样的字符串:
key1=value1 key2=value2 key3=multiple values
它应该与key1=value1
,key2=value2
和key3=multiple values
相匹配。
我已经尝试了以下方法,但是由于我是RegEx新手,所以它不起作用:
string.match(/.*=.+?(?=.*=)/g)
有帮助吗?
谢谢。
答案 0 :(得分:3)
将执行以下操作:(\w+)=(.*?)(?=(?: \w+=)|$)
const string = 'key1=value1 key2=value2 key3=multiple values';
const regex = /(\w+)=(.*?)(?=(?: \w+=)|$)/g
let match;
while((match = regex.exec(string))) {
const [,key, value] = match;
console.log(`Key: ${key} - Value: ${value}`)
}
故障:(\w+)=(.*?)(?=(?: \w+=)|$)
(\w+)=
与密钥匹配。捕获组#1 (.*?)
。匹配值。捕获第2组(?=(?: \w+=)|$)
正向前方看,因此值匹配器将停在字符串的下一个键或末尾,而不将其包括在结果中。如果要在使用//.exec
标志时获取所有捕获组,请使用.match
而不是g
。否则,您将不得不在=
const string = 'key1=value1 key2=value2 key3=multiple values';
const regex = /(\w+)=(.*?)(?=(?: \w+=)|$)/g
let matches = string.match(regex) || [];
for(const match of matches) {
const [key, value] = match.split('=');
console.log(`Key: ${key} - Value: ${value}`)
}
答案 1 :(得分:1)
为防止使用.*?
进行不必要的回溯,另一种选择是使用negated character class并使用负向超前来断言下一个单词不包含等号。
如果只需要匹配键值对,则可以使用:
[^ =]+=[^= ]+(?:(?! [^\s=]+=) [^= ]+)*
部分
[^ =]+=
匹配除空格或=
以外的任何字符1倍以上,然后匹配=
[^= ]+
匹配除空格或=
之外的任意字符1倍以上(?:
非捕获组
(?!
负向前进,断言右边的不是
[^ =]+=
匹配一个空格,除空格或=
以外的任何字符的1倍以上,然后匹配=
)
提前关闭 [^= ]+
如果断言成功,则将一个空格匹配,并将任何字符的1+倍除一个空格或=
)*
关闭非捕获组并重复0次以上以匹配单个单词
const regex = /[^\s=]+=[^=\s]+(?:(?! [^\s=]+=) [^=\s]+)*/g;
const str = `key1=value1 key2=value2 key3=multiple values`;
console.log(str.match(regex));
如果要使用单独的键和值,则可以使用2个捕获组
([^ =]+)=([^= ]+(?:(?! [^\s=]+=) [^= ]+)*)
const regex = /([^ =]+)=([^= ]+(?:(?! [^\s=]+=) [^= ]+)*)/g;
const str = `key1=value1 key2=value2 key3=multiple values`;
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++;
}
console.log(`Key: ${m[1]} Value: ${m[2]}`);
}