JavaScript RegExp无法使用两次?

时间:2014-06-06 14:59:39

标签: javascript regex

我有一个非常严重的问题:

var cat = [ { slug: "test/foo", id: 1}, { slug: "test/bar", id: 1}];
var searchreg = new RegExp("test","g");

cat.forEach(function(item){
  if(searchreg.test(item.slug)){
    console.log(item);
  } 
});

这应该打印出“cat”中的两个项目。但我只得到了第一个。如果我添加更多项目,我只会获得第二个(从第一个开始)。

我知道了:

var cat = [ { slug: "test/foo", id: 1}, { slug: "test/bar", id: 1}];

cat.forEach(function(item){
  var searchreg = new RegExp("test","g");
  if(searchreg.test(item.slug)){
    console.log(item);
  } 
});

但我不明白为什么这不起作用(Chrome) - 任何一个想法?

1 个答案:

答案 0 :(得分:7)

这是因为g(“全局”)标志。当您使用g标志时,RegExp实例具有状态:它们记住它们看到的最后一个匹配的位置,因此它们可以从该点继续(例如,如果您在循环中使用它们)。 (是的,这不是它可能拥有的最好的设计。)所以第一次,它在字符串中找到test(并注意到它不在字符串的 end ) ;第二次,它试图从前一个位置找到前一个字符串中继续的test,当然也找不到它。第三次,因为它知道上次用完了输入,它再次查看输入。

在您的情况下,由于您不需要比第一个实例进一步搜索,只需删除g标记:

var searchreg = /test/; // That's a regex literal, basically: ... = new RegEx("test")

或者,您可以通过将0分配到其lastIndex媒体资源来重置它:

searchreg.lastIndex = 0;
if (searchreg.test(item.slug))

或者,在此特定的用例中,您根本不需要正则表达式:

if (item.slug.indexOf("test") !== -1) {
    // It has "test" in the slug
}