正则表达式
1.引入案例
代码演示:
#需求:判断一个手机号码是否合法. "" import re #regular Expession #使用正则表达式实现上面的需求 # 需求:封装一个函数,判断手机号是否合法? def checkPhone(phone): if len(phone) != 11: return "手机号码长度不符合要求!" if phone[0] != "1": return "手机号码不是1开头!" if not phone.isdigit(): return "手机号码不是全部是数字" return "手机号码格式正确" # print(checkPhone("28617767023")) # 正则验证手机号码是否正确 import re result= re.search("^1\d{10}$","28617767024")) if(result): return "手机号码合法" else: return "手机号码不合法"
2.概述
正则表达式【Regular Expression】,简写为regex,RE,使用单个字符串来描述一系列具有特殊格式的字符串
功能:
a.搜索
b.替换
c.匹配
使用情景:
爬虫
验证手机号,验证邮箱,密码【用户名】
使用正则表达式,需要导入一个模块re import re 常用的函数 # 1.re.match() 匹配字符串是否以指定的正则内容开头,匹配成功返回对象, 匹配失败返回None ''' 第一个参数: 正则表达式 第二个参数: 要验证的字符串 第三个参数: 可选参数,正则表达式修饰符 ''' # \d: 0-9 # +:表示出现1次或者多次 print(re.match("\d+","12345esd")) # <re.Match object; span=(0, 5), match='12345'> print(re.match("\d+","as12345esd")) # None # #2.re.search() 匹配字符串中是否包含指定的正则内容,匹配成功返回对象,匹配失败返回None ''' 第一个参数: 正则表达式 第二个参数: 要验证的字符串 第三个参数: 可选参数,正则表达式修饰符 ''' # 3.re.findall(): 获取所有匹配的内容,会得到一个列表. 若匹配不到内容,返回一个空列表 print(re.findall("\d+","12345asdf9876")) # ['12345', '9876'] print(re.findall("\d+","hello world")) # []
3.使用规则
3.1匹配单个数字或者字符
代码演示:
import re """ ----------匹配单个字符与数字--------- . 匹配除换行符以外的任意字符 [0123456789] []是字符集合,表示匹配方括号中所包含的任意一个字符 [good] 匹配good中任意一个字符 [a-z] 匹配任意小写字母 [A-Z] 匹配任意大写字母 [0-9] 匹配任意数字,类似[0123456789] [0-9a-zA-Z] 匹配任意的数字和字母 [0-9a-zA-Z_] 匹配任意的数字、字母和下划线 [^good] 匹配除了good这几个字母以外的所有字符,中括号里的^称为脱字符,表示不匹配集合中的字符 [^0-9] 匹配所有的非数字字符 \d 匹配数字,效果同[0-9] \D 匹配非数字字符,效果同[^0-9] \w 匹配数字,字母和下划线,效果同[0-9a-zA-Z_] \W 匹配非数字,字母和下划线,效果同[^0-9a-zA-Z_] \s 匹配任意的空白符(空格,回车,换行,制表,换页),效果同[ \r\n\t\f] \S 匹配任意的非空白符,效果同[^ \f\n\r\t] """ #[] :只匹配其中的一位 # - :表示一个区间 print(re.search("he[0-9]llo","he9llo")) # <re.Match object; span=(0, 6), match='he9llo'> print(re.search("go[zxc]od","goxod")) # <re.Match object; span=(0, 5), match='goxod'> print(re.search("he[a-z]llo","hepllo")) # <re.Match object; span=(0, 6), match='hepllo'> print(re.search("hello[0-9a-zA-Z_]","hello9")) print(re.search("hello\d","hello2")) # <re.Match object; span=(0, 6), match='hello2'> print(re.search("hello\D","hello_")) # <re.Match object; span=(0, 6), match='hello_'> print(re.search("hello\w","hello1")) # <re.Match object; span=(0, 6), match='hello1'> print(re.search("hello\W","hello!")) # <re.Match object; span=(0, 6), match='hello!'> print(re.search("mone\sy","mone\ny")) # <re.Match object; span=(0, 6), match='mone\ny'> print(re.search("money[^0-9]","money!")) # <re.Match object; span=(0, 6), match='money!'>
3.2模式修饰符(可选参数)
模式修饰符: 修饰我们写的正则表达式(可选参数) . : 表示匹配除了换行以外的任意单个字符 \n 表示换行 re.S: 可以通过 . 匹配到\n(换行) re.I: 忽略字母大小写 ''' print(re.search("shenzhen.","shenzhen9")) # <re.Match object; span=(0, 9), match='shenzhen9'> print(re.search("shenzhen.","shenzhen\n")) #None print(re.search("shenzhen.","shenzhen\n",re.S)) #<re.Match object; span=(0, 9), match='shenzhen\n'> print(re.search("shenzhen[a-z]","shenzhenS")) # None print(re.search("shenzhen[a-z]","shenzhenS",re.I)) # <re.Match object; span=(0, 9), match='shenzhenS'>
3.3匹配多个字符
import re """ -------------------匹配多个字符------------------------ 说明:下方的x、y、z均为假设的普通字符,n、m(非负整数),不是正则表达式的元字符 (xyz) 匹配小括号内的xyz(作为一个整体去匹配) x? 匹配0个或者1个x x* 匹配0个或者任意多个x(.* 表示匹配0个或者任意多个字符(换行符除外)) x+ 匹配至少一个x x{n} 匹配确定的n个x(n是一个非负整数) x{n,} 匹配至少n个x x{,n} 匹配最多n个x x{n,m} 匹配至少n个最多m个x。注意:n <= m """ import re # 匹配多个字符 ''' ?: 表示 前面的字符可以出现0次或者1次 非贪婪模式 +: 表示 前面的字符可以出现1次或者多次 贪婪模式 *: 表示 前面的字符可以出现0次或者多次 贪婪模式 {}: 表示前面的字符可以出现指定的次数或者次数的范围 贪婪模式 {3}: 表示前面的字符只能出现3次 {3,6}: 表示前面的字符可以出现3-6次 {3,}: 表示前面的字符至少出现3次 {,3}: 表示前面的字符最多出现3次 ''' print(re.search("goog?le","goole")) # <re.Match object; span=(0, 5), match='goole'> 0次的情况 print(re.search("goog?le","google")) # <re.Match object; span=(0, 5), match='goole'> 1次的情况 print(re.search("goog?le","googggggle")) # None g出现多次的情况 print(re.search("goog+le","goole")) # None print(re.search("goog+le","google")) # <re.Match object; span=(0, 6), match='google'> print(re.search("goog+le","googgggggggggggle")) # <re.Match object; span=(0, 17), match='googgggggggggggle'> print(re.search("goog*le","goole")) # <re.Match object; span=(0, 5), match='goole'> print(re.search("goog*le","googgggggggggggle")) # <re.Match object; span=(0, 17), match='googgggggggggggle'> print(re.search("goog{3}le","goole")) # None print(re.search("goog{3}le","google")) # None print(re.search("goog{3}le","googgggggggggle")) # None print(re.search("goog{3}le","googggle")) # <re.Match object; span=(0, 8), match='googggle'> print(re.search("goog{3,6}le","goole")) # None print(re.search("goog{3,6}le","googgle")) # None print(re.search("goog{3,6}le","googgggle")) # <re.Match object; span=(0, 9), match='googgggle'> # {3,}: 表示前面的字符至少出现3次 print(re.search("goog{3,}le","goole")) # None print(re.search("goog{3,}le","google")) # None print(re.search("goog{3,}le","googggle")) # <re.Match object; span=(0, 8), match='googggle'> print(re.search("goog{3,}le","googgggggggggggggggle")) # <re.Match object; span=(0, 21), match='googgggggggggggggggle'> # {,3}: 表示前面的字符最多出现3次 print(re.search("goog{,3}le","googgggle")) # None print(re.search("goog{,3}le","googgle")) #<re.Match object; span=(0, 7), match='googgle'> print(re.search("goog{,3}le","goole")) # <re.Match object; span=(0, 5), match='goole'>
3.4匹配边界字符
代码演示:
import re """ --------------锚字符(边界字符)------------- ^ 行首匹配(以指定字符开头),和在[]里的^不是一个意思 startswith $ 行尾匹配 endswith ^文本$: 完全匹配 print(re.search("^world","world")) # <re.Match object; span=(0, 5), match='world'> print(re.search("^world","hworld")) # None print(re.search("world$","12world")) # <re.Match object; span=(0, 5), match='world'> print(re.search("world$","worlds")) # None print(re.search("^world$","1worlds")) # None print(re.search("^world$","world")) # <re.Match object; span=(0, 5), match='world'> print(re.search("^world$","worldworld")) # None print(re.search("^worl+d$","worlllllllld")) # <re.Match object; span=(0, 12), match='worlllllllld'> # 词边界 \b 匹配一个单词的边界,也就是指单词和空格间的位置 bounds(了解) \B 匹配非单词边界(了解) print(re.search(r"google\b","abcgoogle 123google xcvgoogle456")) # <re.Match object; span=(3, 9), match='google'> print(re.search(r"google\B","abcgoogle 123google xcvgoogle456")) # <re.Match object; span=(23, 29), match='google'> # 转义 \ 让正则表达式中的一些字符失去原有的意义 # \.表示一个单纯的 . 不是正则中的除了换行以外任意一个字符 print(re.search("goog\.le","goog.le")) # 或者 | 正则表达式1 | 正则表达式2 只要满足其中一个正则表达式就能被匹配成功 print(re.search("ef|cd","123ef567")) # <re.Match object; span=(3, 5), match='ef'> """
3.5匹配分组
() : 表示一个整体, 表示分组,然后捕获
代码演示:
tel = "0755-88988888" pattern = '(\d{4})-(\d{8})' result = re.search(pattern,tel) print(result) # <re.Match object; span=(0, 13), match='0755-88988888'> print(result.group()) # 0755-88988888 print(result.group(1)) # 0755 print(result.group(2)) # 88988888 print(result.groups()) # ('0755', '88988888')