python正则表达式 贪婪/非贪婪

主要就是 .* 与 .*? 的区别,.* 是贪婪的,.*? 是非贪婪的例子如下:

    import re 
    line = "Cats are smarter than dogs"
    matchObj1 = re.match( r'(.*)are(.*?)(.*)', line)
    matchObj2 = re.match( r'(.*)are(.+?)(.*)', line)
     
    >>>matchObj1.group(1),matchObj1.group(2),matchObj1.group(3)
    ('Cats ', '', ' smarter than dogs')
    >>>matchObj2.group(1),matchObj2.group(2),matchObj2.group(3)
    ('Cats ', ' ', 'smarter than dogs')

分析:.* 是贪婪的,.*? 是非贪婪的,are精确匹配,所以( .* )即group(1)匹配到的肯定是’Cats ',.*? 是非贪婪的,所以只要后面的满足,(.*?)可以匹配任意长度,于是( . ? )即group(2)就匹配为空,最后(.)即group(3)贪婪匹配,就匹配后面所有的。. *? 与 .+? 唯一区别在于前者可以为空,后者至少匹配一个字符。
除此之外,+ 以及{n,m}也是贪婪的。+? {n,m}?就是非贪婪的。

import re
content = 'Hello 1234567 World_This is a Regex Demo'
result1 = re.match('^He(.*)(\d+)(.*)Demo$', content)
result2 = re.match('^He(.*)(\d+?)(.*)Demo$', content)
result3 = re.match('^He(.*?)(\d+)(.*)Demo$', content)
result4 = re.match('^He(.*?)(\d+?)(.*)Demo$', content)
result5 = re.match('^He(.*?)(.+?)(.*)Demo$', content)
result6 = re.match('^He(.*?)(.+)(.*)Demo$', content)
result7 = re.match('^He(.{2,4})(.*)(.+)Demo$', content)

考虑上面七种情况结果分别是什么(注意:下面有的字符是空格,有的为空,不一样的):

>>>result1.group(1),result1.group(2),result1.group(3)
('llo 123456', '7', ' World_This is a Regex ')

>>>result2.group(1),result2.group(2),result2.group(3)
('llo 123456', '7', ' World_This is a Regex ')

>>>result3.group(1),result3.group(2),result3.group(3)
('llo ', '1234567', ' World_This is a Regex ')

>>>result4.group(1),result4.group(2),result4.group(3)
('llo ', '1', '234567 World_This is a Regex ')

>>>result5.group(1),result5.group(2),result5.group(3)
('', 'l', 'lo 1234567 World_This is a Regex ')

>>>result6.group(1),result6.group(2),result6.group(3)
('', 'llo 1234567 World_This is a Regex ', '')

>>>result7.group(1),result7.group(2),result7.group(3)
('llo ', '1234567 World_This is a Regex', ' ')

总结:

1.*、?、+ 和 {min,max} 是贪婪的,后面再加?就是非贪婪的。

2,不管后面带?还是不带?,含有*,可以匹配空,含有+,至少匹配一个字符,含有{min,max} 至少匹配min个字符。

我把正则表达式的一个小模块总结为以下三个基本元素构成:

元素1元素2元素3

元素1:要匹配的元素,例如 . 表示匹配任意字符,\d表示匹配任意数字,a表示匹配a,等等。

元素2:匹配多少次,例如 * 匹配前一个字符0次或无限次,+ 匹配前一个字符1次或无限次,?匹配前一个字符0次或1次。{n,m} 匹配前一个字符n次到m次。

元素3:空或者是?,若是空,代表元素1和元素2组成贪婪模式,若是?,代表元素1、元素2和元素3组成非贪婪模式。

下面是一些例子:

.* 贪婪匹配尽可能多的任意字符,可以匹配为空。
.*? 非贪婪匹配尽可能少的任意字符,可以匹配为空。
\d+ 贪婪匹配尽可能多的数字,不可以匹配为空,至少匹配一个数字。
\d+? 非贪婪匹配尽可能少的数字,不可以匹配为空,至少匹配一个数字。
.{n,m} 贪婪匹配尽可能多的任意字符,最多m位,最少n位。
.{n,m}? 非贪婪匹配尽可能少的任意字符,最多m位,最少n位。
.+? 非贪婪匹配尽可能少的任意字符,不可以匹配为空,至少匹配一个任意字符。
.+ 贪婪匹配尽可能多的任意字符,不可以匹配为空,至少匹配一个任意字符。
.? 贪婪匹配,可以匹配0或1个任意字符。
.?? 非贪婪匹配,可以匹配0或1个任意字符(不过这两个基本不会有人用)

猜你喜欢

转载自blog.csdn.net/xiaohuihui1994/article/details/83826012