检测一批手机号码是否都符合要求的格式,循环用正则校验,发现无效。去查找了下资料,发现了以前没有注意到地方。git
下面是问题重现:github
const arr=['18311112222','18344445555','2857898098'] const reg = /^1[3-9]\d{9}$/g; const result = arr.find(ele => !reg.test(ele)); console.info({result}); // {result: "18344445555"}
按照上面的正则,第二个号码符合要求,却返回了 false
,去查了资料,发现:正则表达式
若是正则表达式设置了全局标志g
,test()
的执行会改变正则表达式lastIndex
属性。连续的执行test()
方法,后续的执行将会从lastIndex
处开始匹配字符串。
验证一下:ide
const arr=['18311112222','18344445555','2857898098'] const reg = /^1[3-9]\d{9}$/g; const result = arr.find(ele => { const lastIndex = reg.lastIndex; console.info({lastIndex}); return !reg.test(ele); }); // {lastIndex: 0} // {lastIndex: 11}
去掉全局标志 g
,再想想这个场景下没有必要使用全局匹配。ui
使用 String.prototype.search() 。prototype
const arr=['18311112222','18344445555','2857898098'] const reg = /^1[3-9]\d{9}$/g; const result = arr.find(ele => ele.search(reg) === -1);
每次循环匹配的时候,从新声明一个正则。code
const arr=['18311112222','18344445555','2857898098'] const result = arr.find(ele => { const reg = /^1[3-9]\d{9}$/g; return !reg.test(ele); });