目录
问题
- 最近在js中使用正则时,出现了相同的字符串,给相同的正则进行匹配,结果非常规律地返回一次true,一次false,一次true,一次false的结果
- 一开始感觉非常不可思议,因为正则表达式和字符串都一样,进行匹配却得到了不同的结果,而且还固定交替出现true和false。
- 后来直接百度搜"JS正则表达式离奇bug",结果出现了很多关于全局匹配/g的解答,这也正是我遇到的问题的根源所在。
- 下面我们详细聊聊。
全局匹配/g
- 首先我们需要知道正则表达式的匹配方式,总的来说无非两种:
- 搜索:只要求给定字符串中存在可以被正则表达式匹配的字符(或字符串)即算成功
- 例如:
- 给定字符串:"123abc456"
- 正则表达式:/\d+/
- 结果:true
- "123"
- "456"
- 可以看到,整个字符串并不能匹配正则表达式,但它存在可以匹配的子串"123"和"456",因此匹配成功,或者说是搜索成功
- 例如:
- 完全匹配:即给定的字符串必须可以被正则表达式完全匹配才算成功
- 例如:
- 给定字符串:"123abc456"
- 正则表达式:/^\d+$/
- 注意表达式的开头多了个^(即从字符串开头)和末尾的$(到字符串的结尾),表示整个字符串得从头到尾正确匹配我们的正则表达式
- 结果:false
- 由于字符串不能匹配正则表达式,因此匹配失败
- 例如:
- 搜索:只要求给定字符串中存在可以被正则表达式匹配的字符(或字符串)即算成功
- 而本文的问题就出现在搜索模式上
- 全局匹配。在声明正则表达式之后加上g,如:
- /\d+/g 或 new RegExp("\\d+", "g")
- 注意全局匹配是搜索的方式
- 之前就是理解错了全局匹配的意思,以为它是完全匹配,所以用错了
分析
- 使用全局匹配时,正则表达式对象的 lastIndex 属性需要注意:
- 初始化默认为0
- 若匹配成功,则lastIndex被置为被匹配的子字符串的末尾下标再+1
- 若匹配失败,则lastIndex被置为0
- 每次使用该正则表达式对象去匹配时,都会从这个lastIndex开始
- 因此,在文章开头,我们使用同一个全局匹配模式的正则对象去匹配时,过程如下:
- 假设字符串为"123456"
- 假设正则表达式为:/\d+/g
- 第一次使用,lastIndex初始为0,字符串整个被匹配,lastIndex = 6(被匹配字符串的末尾(字符6)的下标5 + 1),匹配成功
- 第二次使用,从lastIndex=6开始拿字符串,正则对象拿到的待匹配字符串其实就是空串 "",显然空串不能匹配我们的正则,因此匹配失败,注意此时lastIndex因匹配失败被置为0
- 第三次使用,从lastIndex=0开始,又和第一次使用一样,匹配成功且lastIndex = 6
- 第四次使用,从lastIndex=6开始,和第二次使用一样,拿到了空串,匹配失败且lastIndex = 0
- 因此会出现交替的成功、失败
解决
- 知道了原因后其实就解决就简单了,这里主要由四种办法:
- 1:简单粗暴把正则表达式的全局匹配/g去掉,使用完全匹配,即创建正则对象时不使用/g参数
- 2:每次使用前,把正则对象的 lastIndex 手动置0
- 3:每次都重新创建正则对象,因为初始化默认的lastIndex为0,本质和第二种办法差不多
- 4:奇特的方法,既然是本应匹配成功的时候却交替的出现成功和失败,而本应匹配失败的时候是一直出现失败。那么我们就可以连续两次进行匹配,将两次的结果或 | 起来就可以了。
- 如:字符串str = "123456" 和正则表达式 reg = /\d+/g
- return (reg.test(str) | reg.test(str));
- 但最好还是直接用第一种,明确你使用正则的目的
Полезные советы по покупке диплома о высшем образовании без риска
Тут можно преобрести огнеупорный сейф купить сейф пожаростойкий
Тут можно преобрести сейф для оружия цены оружейные сейфы купить в москве
найти это электрик томск
Здесь можно преобрести купить сейф оптом сейф купить москва
http://canadiandrugsgate.com/# over the counter ed treatment
Продолжение https://xn—-7sbbajqthmir8bngi.xn--p1acf/ozempik-134-mg-ml-rastvor-dlya-podkozhnogo-vvedeniya-v-komplekte-s-iglami-novofajn-plyus-6sht-15-ml-1-sht/
Следующая страница [url=https://xn—-jtbjfcbdfr0afji4m.xn--p1ai]электрик томск[/url]
Всё, что нужно знать о покупке аттестата о среднем образовании без рисков
blogsfere.com/viewtopic.php?t=190874
купить диплом ессентуки 1oriks-diplom199.ru .
mexican border pharmacies shipping to usa: mexican pharmacy online – reputable mexican pharmacies online
посмотреть на этом сайте электрик томск
purple pharmacy mexico price list mexican pharmacy online medications buying from online mexican pharmacy
здесь https://xn—-7sbbajqthmir8bngi.xn--p1acf/ozempik-134-mg-ml-rastvor-dlya-podkozhnogo-vvedeniya-v-komplekte-s-iglami-novofajn-plyus-6sht-15-ml-1-sht/
Как официально приобрести аттестат 11 класса с минимальными затратами времени
Официальная покупка диплома вуза с упрощенной программой обучения
Всё, что нужно знать о покупке аттестата о среднем образовании
п»їlegitimate online pharmacies india Indian pharmacy to USA Online medicine order
перенаправляется сюда https://xn—-7sbbajqthmir8bngi.xn--p1acf/mundzharo-mounjaro/
Удивительно, но купить диплом кандидата наук оказалось не так сложно
vanbroecanimations.online/kupit-attestat-za-11-klass-moskva.html
indian pharmacy: Online Indian pharmacy – buy prescription drugs from india
веб-сайте [url=https://xn—-jtbjfcbdfr0afji4m.xn--p1ai]электрик томск[/url]
Тут можно преобрести купить оружейный сейф оружейные сейфы и шкафы для охотничьего ружья
indian pharmacy: indianpharmacyeasy.com – indianpharmacy com
Подробнее электрик томск
https://indianpharmacyeasy.com/# pharmacy website india
top erection pills: Best Canadian online pharmacy – pharmacy drugs
https://canadiandrugsgate.com/# online meds for ed
Как официально купить аттестат 11 класса с упрощенным обучением в Москве
Тут можно преобрести огнестойкие сейфы купить сейф москва огнестойкий купить
Пошаговая инструкция по безопасной покупке диплома о высшем образовании
indian pharmacy online: Online Indian pharmacy – reputable indian pharmacies
Alpha bites reviews
вывод из запоя ростов на дону https://alhambra.bestforums.org/viewtopic.php?f=2&t=46349 .
вывод из запоя на дому ростов https://www.forumbar.anihub.me/viewtopic.php?id=9747 .
вывод из запоя цены ростов на дону http://business.0pk.me/viewtopic.php?id=37942#p224618 .
вывод из запоя на дому ростов круглосуточно sportandpolitics.ukrbb.net/viewtopic.php?f=24&t=17793v .
вывод из запоя круглосуточно http://www.sergiev.0pk.me/viewtopic.php?id=3452 .
вывод из запоя в стационаре ростов http://www.familyportal.forumrom.com/viewtopic.php?id=28559 .
вывод из запоя круглосуточно ростов-на-дону http://ideya.forums.party/viewtopic.php?id=652/ .
вывод из запоя цена ростов https://vip.mybb.rocks/viewtopic.php?id=7670/ .
вывод. из. запоя. на. дому. ростов. http://to.iboard.ws/viewtopic.php?id=8058 .
вывод. из. запоя. анонимно. ростов. вывод. из. запоя. анонимно. ростов. .
вывод из запоя на дому ростов цены http://www.rubiz.forum.cool/viewtopic.php?id=3742 .
анонимный вывод из запоя ростов анонимный вывод из запоя ростов .
вывод из запоя цены ростов на дону http://to.iboard.ws/viewtopic.php?id=8058 .
быстрый вывод из запоя ростов http://forumbar.anihub.me/viewtopic.php?id=9747/ .
вывод из запоя цены ростов на дону alhambra.bestforums.org/viewtopic.php?f=2&t=46349 .
вывод из запоя на дому ростов-на-дону вывод из запоя на дому ростов-на-дону .
вывод из запоя ростов http://ideya.forums.party/viewtopic.php?id=652/ .