python内置模块之re模块


内容概要

  • re模块常用方法

  • findall

  • search

  • match

  • re模块其他方法

  • split

  • sub

  • subn

  • compile

  • finditer

  • findall 对无名分组优先展示

  • re实战之爬取红牛分公司数据

内容详细

re模块常用方法

在python要想使用正则必须借助于模块,re就是其中之一

1、findall

查找字符串中所有匹配到的字符,并返回一个列表,
没有匹配数据则返回一个空列表

import re

re.findall('正则表达式','带匹配的文本')  # 根据正则匹配除所有符合条件的数据
res = re.findall('b','eva jason jackson')
print(res)  # ['a', 'a', 'a']

2、search

查找字符串中的指定的字符,匹配到一个就立刻停止,并返回一个对象,需要用group方法取值

res = re.search('正则表达式','带匹配的文本')  # 根据正则匹配到一个符合条件的就结束
res = re.search('a','eva jason jackson')
print(res)  # 结果对象
print(res.group())  # 正在的结果
if res:
    print(res.group())
else:
    print('不好意思 没有找到')

如果没有匹配到字符会返回一个None,并且调用group后会报错

3、match

查找字符串中的指定的字符,只匹配开头的字符,返回一个对象,需要用group方法取值

res = re.match('a','abac')  # 根据正则从头开始匹配(文本内容必须在开头匹配上)
print(res)
print(res.group())
if res:
    print(res.group())
else:
    print('不好意思 没有找到')

如果没有符合条件的数据 那么match返回None 并且使用group会直接报错

re模块其他方法

1、split

类似字符串的切割,不过这里就算切割字母左右没有字符也会切割出一个空 ""

import re
先按'a'分割得到''和'bcd',在对''和'bcd'分别按'b'分割
res = re.split('[ab]','abcd')
print(res)  # ['', '', 'cd']

2、sub

类似字符串内置方法的replace

# 类似于字符串类型的replace方法
res = re.sub('\d','H','eva3jason4yuan4',1)  # 替换正则匹配到的内容
res = re.sub('\d','H','eva3jason4yuan4')  # 不写默认替换所有
print(res)  # evaHjason4yuan4

3、subn

替换完成后会返回一个元组 ("更换后的字符串", 被更换的个数)

"""返回元组 并提示替换了几处"""
# res = re.subn('\d','H','eva3jason4yuan4',1)
# print(res)  # ('evaHjason4yuan4', 1)
# res = re.subn('\d','H','eva3jason4yuan4')
# print(res)  # ('evaHjasonHyuanH', 3)

4、compile

定义一个固定的正则表达式,可以多次重复使用匹配不同的字符串

point = re.compile('(.*?)')
res1 = point.findall(date1)
res2 = point.search(date2)
res3 = point.match(date3)
res3 = point.finditer(date4)

regexp_obj = re.compile('\d+')
res = regexp_obj.search('absd213j1hjj213jk')
res1 = regexp_obj.match('123hhkj2h1j3123')
res2 = regexp_obj.findall('1213k1j2jhj21j3123hh')
print(res,res1,res2)

5、finditer

与findall的作用一致,但findall返回的是一个列表,当数据量很大,会特别占用内存空间

而finditer会返回一个可迭代对象,当需要数据时,迭代获取即可

# res = re.finditer('\d+','ashdklah21h23kj12jk3klj112312121kl131')
# print([i.group() for i in res])

6、search对分组的索引取值展示

# res = re.search('^[1-9](\d{14})(\d{2}[0-9x])?$','110105199812067023')
# print(res)
# print(res.group())  # 110105199812067023
# print(res.group(1))  # 10105199812067
# print(res.group(2))  # 023

7、findall 对无名分组优先展示

findall针对分组优先展示 无名分组

res = re.findall("^[1-9]\d{14}(\d{2}[0-9x])?$",'110105199812067023')
print(res)  # ['023']

取消分组优先展示 无名分组

res1 = re.findall("^[1-9](?:\d{14})(?:\d{2}[0-9x])?$",'110105199812067023')
print(res1)

8、有名分组

res = re.search('^[1-9](?P\d{14})(?P\d{2}[0-9x])?$','110105199812067023')
print(res)
print(res.group())  # 110105199812067023
print(res.group(1))  # 10105199812067  无名分组的取值方式(索引取)
print(res.group('xxx'))  # 10105199812067
print(res.group('ooo'))  # 023

正则实战案例

1、登录红牛官网 点击分支结构网页 http://www.redbull.com.cn/about/branch
2、如图所示,爬取所有分公司名称,地址,邮箱,电话等信息

3、右键点击查看网页源代码,全选网页代码复制到pychram的文件中

4、新建py文件,打开并读取网页源码文件,用正则表达式筛选分公司信息

import re

# 读取带匹配的数据
with open(r'a.txt', 'r', encoding='utf8') as f:
    data = f.read()
# 利用正则匹配数据
# 分公司名称
title_list = re.findall('

(.*?)

', data) # print(title_list) # 分公司地址 address_list = re.findall("

(.*?)

", data) # print(address_list) # 分公司邮箱 email_list = re.findall("

(.*?)

", data) # print(email_list) # 分公司电话 phone_list = re.findall("

(.*?)

", data) res = zip(title_list, address_list, email_list, phone_list) for data_tuple in res: print(""" 公司名称:%s 公司地址:%s 公司邮箱:%s 公司电话:%s """ % (data_tuple[0], data_tuple[1], data_tuple[2], data_tuple[3]))