(1)选用示例语言
(2)文本的获取
使用requests
库来获取B站首页html页面,将其写入到文本中,避免每次测试都需要动用网络资源
immport requests
# 将html页面写入到文本
with open("data.html","w",encoding="utf-8") as html:
response = requests.get("https://www.bilibili.com/")
html.write(response.text)
# 读取文本内容
text = ''
with open("data.html",'r',encoding="utf-8") as html:
text = html.read()
(3)正则表达式的效果查看
(1)re
库
导入re
(regular expression)库
import re
(2)re.Pattern
类
该类为re库中的一个类,通过传入正则表达式构造该对象,用于去寻找匹配的字符串
pattern = re.compile(r"正则表达式")
通常使用 r"字符串"来表示这是一个原始字符串,即不对一些特殊字符,如"\","\t"等进行转义,一下为两者区别的示例:
>>> str = "this is a string.\n \tand this is the second line."
>>> print(str)
this is a string.
and this is the second line.
>>> str = r"this is a string.\n \tand this is the second line."
>>> print(str)
this is a string.\n \tand this is the second line.
(3)pattern.finall(文本内容)
该方法为pattern对象的方法,用于依据正则表达式在匹配传入文本中的所有内容,将符合规则的字符串存入列表中,最后返回该列表
re.compile(r"哔哩哔哩")
strList = patern.findall(text)
print(strList)
结果:
<class 'list'>
['哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩
哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩',
'哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔
哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩']
正则表达式的特殊字符包括:. * + ? \ [ ] ^ $ { } | ( )
(1)任意字符.
.
表示要匹配除了换行符之外的任何单个字符
python示例:
pattern = re.compile(r'.哩.哩')
strList = pattern.findall(text)
print(strList)
结果:
['哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩
哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩',
'哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔
哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩', '哔哩哔哩']
可以设置字符匹配模式为DOTALL
模式来使得.
匹配换行符
content = '''
'''
pattern = re.compile(r'class=\"t1\">.*?(.*?)', re.DOTALL)
print(pattern.findall())
[Python开发工程师, java开发工程师]
(2)任意个数字符*
*
表示匹配前面子表达式任意次
(2)存在或多个字符+
(3)非确定字符是否存在?
(4)指定字符出现次数{m,n}
{m,n}
表示匹配前面的子表达式m至n次,它会以最大匹配次数来进行匹配
{m,}
表示匹配前面的子表达式至少m次,它会以最大匹配次数来进行匹配
{m}
表示匹配前面的子表达式m次,它只会匹配m次,即时后面还有可匹配的
(5)指定字符范围[]
[abcd]
表示该字符只要符合为括号中的一项即可
[m-n]
表示在m至n的范围内都符合该规则
特殊字符在[]
中不再表示其特殊含义,但是\
依旧会有转义作用
如果在方括号中使用^
,表示匹配不是括号中的字符
(6)开头^
表示匹配文本的起始位置
如果是单行模式 ,表示匹配整个文本的开头位置。
比如:
text = """PS E:\PythonStudy> python -u "e:\PythonStudy\regexp\reglearn.py"
['Alice', 'Bob']
PS E:\PythonStudy> python -u "e:\PythonStudy\regexp\reglearn.py"
['Alice', 'Bob', '大卫']
PS E:\PythonStudy> python -u "e:\PythonStudy\regexp\reglearn.py"
['Alice', 'Bob']
"""
pattern = re.compile(r'^P.*?>')
strList = pattern.findall(text)
print(strList)
['PS E:\\PythonStudy>']
如果是多行模式 ,表示匹配文本每行的开头位置
比如:
pattern = re.compile(r'^P.*>',re.MULTILINE)
strList = pattern.findall(text)
print(strList)
['PS E:\\PythonStudy>', 'PS E:\\PythonStudy>', 'PS E:\\PythonStudy>']
re.MUTILINE
或者re.M
构建pattern对象,实现多行匹配模式(7)结尾$
表示匹配文本的结束位置
如果是单行模式,表示匹配整个文本的结尾位置
text = """Alice say : <== privateKey
Bob say : ==> publicKey
"""
pattern = re.compile(r'\S*$')
strList = pattern.findall(text)
print(strList)
['publicKey', '', '']
如果是多行模式,表示匹配文本每行的结尾位置
pattern = re.compile(r'\S*$',re.M)
strList = pattern.findall(text)
print(strList)
['privateKey', '', 'publicKey', '', '']
(8)其中之一|
(9)转义\
对特殊字符进行转义,用于将特殊字符看做普通字符,参与匹配过程
匹配某种字符类型:
模式 | 含义 |
---|---|
\w | 匹配数字字母下划线等价于[ a-zA-Z0-9 ],缺省情况下也包括Unicode文字字符,可以指定为只包括Ascll字符 |
\W | 匹配非数字字母下划线,等价于[ ^a-zA-Z0-9 ] |
\s | 匹配任意空白字符,等价于 [ \t\n\r\f ](tab,换行,空格) |
\S | 匹配任意非空字符,等价于[ ^\t\n\r\f] |
\d | 匹配任意数字,等价于 [0-9]。 |
\D | 匹配任意非数字,等价于[ ^0-9 ] |
\A | 匹配字符串开始 |
\Z | 匹配字符串结束,如果是存在换行,只匹配到换行前的结束字符串。 |
\z | 匹配字符串结束 |
\G | 匹配最后匹配完成的位置。 |
\b | 匹配一个单词边界,也就是指单词和空格间的位置。例如, ‘er\b’ 可以匹配"never" 中的 ‘er’,但不能匹配 “verb” 中的 ‘er’。 |
\B | 匹配非单词边界。‘er\B’ 能匹配 “verb” 中的 ‘er’,但不能匹配 “never” 中的 ‘er’。 |
\n, \t, \f,\v | 匹配一个换行符,等价于 \x0a 和 \cJ;匹配一个制表符, 等价于 \x09 和 \cI;等;匹配一个换页符,等价于 \x0c 和 \cL;匹配一个垂直制表符。等价于 \x0b 和 \cK |
\num | 匹配 num,其中 num 是一个正整数。对所获取的匹配的引用。例如,’(.)\1’ 匹配两个连续的相同字符 |
菜鸟教程
对于\w,如果不指定风格,则会包含unicode编码字符
比如:
text = """
Alice
Bob
大卫
"""
pattern = re.compile(r'\w{2,5}')
strList = pattern.findall(text)
print(strList)//['Alice', 'Bob', '大卫']
可以使用指定方式re.A,或则re.ASCII指定匹配模式为字符只包含ascii码的字符
pattern = re.compile(r'\w{2,5}',re.A)
strList = pattern.findall(text)
print(strList)//['Alice', 'Bob']
(1)分组介绍
()
的方式来对结果进行分组,从而获取匹配字符串中的有效信息(2)分组的使用
python代码示例:
text = """
2020-4-13 22:04:27 Alice : hello,world.
2020-4-13 22:04:32 Bob : nice to meet you.
"""
# 使用分组
pattern = re.compile(r'(\w*)\s:\s(.*).',re.M)
strList = pattern.findall(text)
print(strList)
# 不使用分组
pattern = re.compile(r'\w*\s:\s.*.',re.M)
strList = pattern.findall(text)
print(strList)
结果:
[('Alice', 'hello,world'), ('Bob', 'nice to meet you')]
['Alice : hello,world.', 'Bob : nice to meet you.']
通过使用()
将所需要的信息分离出来,最终会以元素为元组的列表作为返回结果
(1)贪婪模式
贪婪模式是指在匹配时会尽可能的多匹配,当匹配的字符串已经符合要求时,如果后面的字符串依旧符合要求,则会继续进行匹配,直到后面的字符串不符合规则
+
,*
都为贪婪模式,会尽可能地去匹配
(2)非贪婪模式
该模式匹配到第一个符合表达式规则的字符串就会停止
通过在+
,*
,{}
后面加上?
来使之以非贪婪模式匹配,只要满足第一次符合规则的情况就可以
(1)re.match(pattern, string, flags=0
)
该方法只匹配字符串的开始,如果字符串开始不符合正则表达式,则匹配失败,函数返回 None;如果匹配成功返回match对象
通过group方法来获得结果
text = """http:www.pics.com/cat.jpg
http:www.imgs.com/dog.png
http:www.imgs.com/doge.png
http:www.pics.com/bird.gif
http:www.pics.com/horse.jpeg
"""
pattern = 'http.*\.(.*)\.com.*(\S*\.\S*)'
print(re.match(pattern, text).group(0))
print(re.match(pattern, text).group(1))
print(re.match(pattern, text).group(2))
print(re.match(pattern, text).group())
http:www.pics.com/cat.jpg
pics
.jpg
http:www.pics.com/cat.jpg
(2)re.search(pattern, string, flags=0)
(3)re.sub(pattern, repl, string, count=0, flags=0)
re.sub用于替换字符串中的匹配项
该方法返回一个新的被替换的字符串,源字符串不受影响
示例:
print(re.sub(pattern,"哈哈",text))
哈哈:www.pics.com/cat.jpg
哈哈:www.imgs.com/dog.png
哈哈:www.imgs.com/doge.png
哈哈:www.pics.com/bird.gif
哈哈:www.pics.com/horse.jpeg
(4)re.compile(pattern[, flags])
compile 函数用于编译正则表达式,生成一个正则表达式( Pattern )对象,提供match()和search() 这两个函数使用
Pattern对象拥有re中的函数方法,即re.函数的Pattern参数为本身
例:
pattern = re.compile(r'pics.*/(\S+).*')
print(re.sub(pattern,"哈哈",text))
print(pattern.sub("哈哈",text)) # 两者效果相同
python源码:
# 这是re.search方法,其它类似
def search(pattern, string, flags=0):
"""Scan through string looking for a match to the pattern, returning
a Match object, or None if no match was found."""
return _compile(pattern, flags).search(string)
(5)re.findall(string[, pos[, endpos]])
(6)re.finditer(pattern, string, flags=0)
和 findall 类似,在字符串中找到正则表达式所匹配的所有子串的match
对象,并把它们作为一个迭代器返回
示例
pattern = re.compile(r'pics.*/(\S+).*')
for match in pattern.finditer(text):
print(match.group(1))
cat.jpg
bird.gif
horse.jpeg
(7)re.split(pattern, string[, maxsplit=0, flags=0])
split 方法按照能够匹配的子串将字符串分割后返回列表,它的使用形式如下
pattern = re.compile(r'/')
print(pattern.split(text))
['http:www.pics.com', 'cat.jpg\nhttp:www.imgs.com', 'dog.png\nhttp:www.imgs.com', 'doge.png\nhttp:www.pics.com', 'bird.gif\nhttp:www.pics.com', 'horse.jpeg\n']
(1)python中的正则表达式匹配模式
源码
class RegexFlag(enum.IntFlag):
ASCII = sre_compile.SRE_FLAG_ASCII # assume ascii "locale" 指定字符集为ascii码
IGNORECASE = sre_compile.SRE_FLAG_IGNORECASE # ignore case 忽略大小写
LOCALE = sre_compile.SRE_FLAG_LOCALE # assume current 8-bit locale
UNICODE = sre_compile.SRE_FLAG_UNICODE # assume unicode "locale" 根据Unicode字符集解析字符。这个标志影响 \w, \W, \b, \B
MULTILINE = sre_compile.SRE_FLAG_MULTILINE # make anchors look for newline 多行匹配
DOTALL = sre_compile.SRE_FLAG_DOTALL # make dot match newline 使 . 匹配包括换行在内的所有字符
VERBOSE = sre_compile.SRE_FLAG_VERBOSE # ignore whitespace and comments 这个选项忽略规则表达式中的空白和注释,并允许使用 ’#’ 来引导一个注释。这样可以让你把规则写得更美观些
A = ASCII
I = IGNORECASE
L = LOCALE
U = UNICODE
M = MULTILINE
S = DOTALL
X = VERBOSE
# sre extensions (experimental, don't rely on these)
TEMPLATE = sre_compile.SRE_FLAG_TEMPLATE # disable backtracking
T = TEMPLATE
DEBUG = sre_compile.SRE_FLAG_DEBUG # dump pattern after compilation