正则表达式断言和分组捕获以及贪婪
正则的写法比较多,而且方法也很多,做到提取,替换,都需要不同的正则来
一,零宽断言(正向先行断言,负向先行断言,负向后行断言,正向后行断言)
断言: 断定正则里面有什么字符
零宽:就是欸有宽度,只匹配位置,不占字符,就是匹配结果不返回断言的正则本身
通过提取字符例子来看:
const string = "<span>阅读数量:345</span>"
我现在通过不同的断言提取345
1. 正向先行断言
语法: (?=pattern)
作用:匹配pattern前面的内容,不返回自身
我需要提取string 里面的345, 正向线性断言正则, 我现在就是需要拿到</span>前面的内容,可以有如下正则;
let regexp = /.+(?=<\/span>)/g
匹配
string.match(regexp) 得到 数组 如图
String.prototype.match
方法检索返回一个字符串匹配正则表达式的结果。
但是我们只需要匹配数字,可以设置 \d+ 如图
2. 正向后行断言(正后顾)
语法:(?<=parttern)
作用:匹配表达式后面的内容不返回自身
有了前面的正向先行匹配,这个就比较简单理解,可以写出如下正则
const regexp = /(?<=<span>阅读数量:)\d+/g
3. 负向先行断言(复前瞻)
语法:(?!parttern)
作用:匹配非pattern前面的内容,不返回自身
例如 str = '我爱祖国,我是祖国的花朵' ; 我要找到不是“的花朵”前面的祖国, 可以写出如下正则
const regexp = /祖国(?!的花朵)/g
4. 负向后行断言
语法: (?<!pattern)
作用:匹配非pattern表达式后面的内容,不返回本身
例如对 "regex represents regular expression" 这个字符串;要想匹配单词开头的 re
const reg = /(?<!\w)re/ 匹配非w中的re
对于这 4 个断言的理解,可以从两个方面入手:
-
1、关于先行(lookahead)和后行(lookbehind):正则表达式引擎在执行字符串和表达式匹配时,会从头到尾(从前到后)连续扫描字符串中的字符,设想有一个扫描指针指向字符边界处并随匹配过程移动。先行断言,是当扫描指针位于某处时,引擎会尝试匹配指针还未扫过的字符,先于指针到达该字符,故称为先行。后行断言,引擎会尝试匹配指针已扫过的字符,后于指针到达该字符,故称为后行。2、关于正向(positive)和负向(negative):正向就表示匹配括号中的表达式,负向表示不匹配。
- 先行和后行:后行断言 (?<=pattern)、(?<!pattern) 中,有个小于号,同时也是箭头,对于自左至右的文本方向,这个箭头是指向后的,这也比较符合我们的习惯。把小于号去掉,就是先行断言。
- 正向和负向:不等于 (!=)、逻辑非 (!) 都是用 !号来表示,所以有 ! 号的形式表示不匹配、负向;将 ! 号换成 = 号,就表示匹配、正向。
二,捕获和非捕获
也就是分组匹配
捕获组:匹配子表达式的内容,把匹配结果保存到内存中中数字编号或显示命名的组里,以深度优先进行编号,之后可以通过序号或名称来使用这些匹配结果。
解释:从表达式左侧开始,每出现一个左括号和它对应的右括号之间的内容为一个分组,在分组中,第0组为整个表达式,第一组开始为分组。
比如固定电话的:020-85653333
他的正则表达式为:(0\d{2})-(\d{8})
按照左括号的顺序,这个表达式有如下分组:
我们用js 来验证一下:
reg.exec可以提取到不同的分组, 例如028 , 88773322
2. 以此类推 命名编号捕获组:
拿到年月日
分组捕获电话号码, 使用match匹配正则会有一个数组, 以电话号码举例分别如下
在groups中可以通过命名正则上面的命名来获取捕获值
3. 非捕获组:
语法:(?:exp)
解释:和捕获组刚好相反,它用来标识那些不需要捕获的分组,说的通俗一点,就是你可以根据需要去保存你的分组。
还是匹配电话号码 如果不想要前面的区号 就在区号前面加?:
let phone2 = '027-99887766'.match(/(?:0\d{2})-(\d{8})/)
三,反向引用
四, 贪婪和非贪婪
贪婪: 尽可能多的匹配到符合条件的字符串
非贪婪:在贪婪量词后面加? 可以让贪婪正则变成懒惰正则 ?
表示最小化匹配, 只能用在量词后面,表示如果多个文本段同时满足条件,则匹配最短的
例如匹配'<span></span> <span></span>' 包含几对’<span></span>‘呢 ,一般认为2个,实际上正则可以匹配到一整段了会
如果想不匹配整段,使用如下正则<span>.*?</span>
原作者姓名:假不理
原出处:掘金
原文链接:https://juejin.im/post/5b96a8e2