我试图解析以下类型的字符串:

[key:"val" key2:"val2"]

其中有任意键:“val”对在里面。我想获取键名和值。 对于那些好奇的人,我试图解析任务战士的数据库格式。

这是我的测试字符串:

[description:"aoeu" uuid:"123sth"]

这意味着除了空格之外,任何东西都可以放在键或值中,冒号周围没有空格,值总是在双引号中。

在node中,这是我的输出:

[deuteronomy][gatlin][~]$ node
> var re = /^\[(?:(.+?):"(.+?)"\s*)+\]$/g
> re.exec('[description:"aoeu" uuid:"123sth"]');
[ '[description:"aoeu" uuid:"123sth"]',
  'uuid',
  '123sth',
  index: 0,
  input: '[description:"aoeu" uuid:"123sth"]' ]

但是描述:“aoeu”也符合这个模式。我怎么能得到所有的比赛回来?


当前回答

我强烈推荐使用String.match()函数,并为它创建一个相关的RegEx。我的例子是一个字符串列表,在扫描用户输入的关键字和短语时,这通常是必要的。

    // 1) Define keywords
    var keywords = ['apple', 'orange', 'banana'];

    // 2) Create regex, pass "i" for case-insensitive and "g" for global search
    regex = new RegExp("(" + keywords.join('|') + ")", "ig");
    => /(apple|orange|banana)/gi

    // 3) Match it against any string to get all matches 
    "Test string for ORANGE's or apples were mentioned".match(regex);
    => ["ORANGE", "apple"]

希望这能有所帮助!

其他回答

要遍历所有匹配项,可以使用replace函数:

var re = /\s*([^[:]+):\"([^"]+)"/g;
var s = '[description:"aoeu" uuid:"123sth"]';

s.replace(re, function(match, g1, g2) { console.log(g1, g2); });

Str.match (pattern),如果pattern具有全局标志g,将以数组形式返回所有匹配项。

例如:

const str = '除了@Emran, @Raju和@Noman,我们都在那里'; console.log ( str.match (/ @ \ w * / g) ); // Will log ["@Emran", "@Raju", "@Noman"]

下面是我得到匹配的函数:

function getAllMatches(regex, text) {
    if (regex.constructor !== RegExp) {
        throw new Error('not RegExp');
    }

    var res = [];
    var match = null;

    if (regex.global) {
        while (match = regex.exec(text)) {
            res.push(match);
        }
    }
    else {
        if (match = regex.exec(text)) {
            res.push(match);
        }
    }

    return res;
}

// Example:

var regex = /abc|def|ghi/g;
var res = getAllMatches(regex, 'abcdefghi');

res.forEach(function (item) {
    console.log(item[0]);
});

用这个……

var all_matches = your_string.match(re);
console.log(all_matches)

它将返回一个包含所有匹配项的数组…这很好.... 但是记住它不会考虑分组,它只会返回完整的匹配。

str.match(/regex/g)

以数组形式返回所有匹配项。

如果出于某种神秘的原因,您需要exec附带的额外信息,作为前面答案的替代方案,您可以使用递归函数来代替循环,如下所示(这看起来也很酷:)。

function findMatches(regex, str, matches = []) {
   const res = regex.exec(str)
   res && matches.push(res) && findMatches(regex, str, matches)
   return matches
}

// Usage
const matches = findMatches(/regex/g, str)

正如前面的评论中所述,在regex定义的末尾加上g,以便在每次执行时将指针向前移动,这很重要。