赞
踩
举个例子:
从字符串"1234jfvpsjgmbk780a15801879957**82mmn1234lciclshalcojfbg…"里找出手机号码,这个字符串可能有上万个字符,不可能人眼一个个找,使用正则表达式,告诉它,凡是158,138,182等开头,并且连续11个都是数字的,就是手机号码。那么凡是158,138,182等开头,并且连续11个都是数字的,就是手机号码,这段描述就是正则表达式的文字描述,接下来,我们要把它转化为专业的python描述。
import re
# "alexsel"是模式字符串,即正则表达式,"gtuanalesxalexselericapp"则为待匹配的字符串
result = re.findall("alexsel","gtuanalesxalexselericapp")
print(result)
result:
['alexsel']
import re
result = re.findall("[od]", "Hello,World.")
print(result)
result:
['o', 'o', 'd']
re.findall("(ab)+","aabz1144cabcd")
result:
['ab', 'ab']
re.findall("alexsel{3}","aaaalexselllll")
result:
['alexselll']
数量词 | 含义 | 举例 | 结果 |
---|---|---|---|
符号 * | 匹配前一个字符0次或无限次 | re.findall(“lo*”, “Hello,World.”) | [‘l’, ‘lo’, ‘l’] |
符号 + | 匹配前一个字符1次或无限次 | re.findall(“lo+”, “Hello,World.”) | [‘lo’] |
符号? | 匹配前一个字符0次或1次 | re.findall(“lo?”, “Hello,World.”) | re.findall(“lo?”, “Hello,World.”) |
{m} | 匹配前一个字符m次 | re.findall(“lo{1}”, “loooxooloox”) | [‘lo’, ‘lo’] |
{m,} | 前一个字符至少出现m次 | re.findall(“lo{2,}”, “loooxooloolox”) | [‘looo’, ‘loo’],贪婪方式 |
{m,n} | 匹配前一个字符m~n次 | re.findall(“lo{2,3}”, “loooxooloolox”) | [‘looo’, ‘loo’], 贪婪方式 |
字符 | 含义 | 举例 | 结果 |
---|---|---|---|
\d | 匹配任何十进制数字;相当于类 [0-9] | re.findall(r"a\d{3,}", “bca12345a78a985”) | [‘a12345’, ‘a985’] |
\D | 与 \d 相反,匹配任何非十进制数字的字符;相当于类 [^0-9] | re.findall(r"a\D{2}", “bca12345a78a985amdax”) | [‘amd’] |
\w | 匹配字母数字及下划线,相当于[a-zA-Z0-9_] | re.findall(r"\w\d{2}", “hello95aa2d78”) | [‘o95’, ‘d78’] |
\W | 与 \w 相反 | ||
\s 匹配任何空白字符 | (包含空格、换行符、制表符等);相当于类 [ \t\n\r\f\v] | re.findall(r"\s\w", “hello world hello \nChina”) | [’ w’, ’ h’, ‘\nC’] |
\S | 与 \s 相反,匹配任何非空白字符;相当于类 [^ \t\n\r\f\v] | ||
. | 匹配一个除了换行符任意一个字符 | ||
\\ | 原意的\ | ||
[^] | 相当于非运算符,除了后面的,其它的都行 |
字符 | 含义 | 举例 | 结果 |
---|---|---|---|
\b | 匹配单词的开始或结束,即单词的边界,boundary | re.findall(r"\babc\b",“abc sds abc abcd”) | [‘abc’, ‘abc’] |
\B | 与 \b 相反 | re.findall(r"\Babc\B",“abc sds abc cabcd”) | [‘abc’] |
\A | 从字符串的开始处匹配,A是字母里的第一个,用于指示开始处 | re.findall(r"\Aabc",“abc sds abc abcd”) | [‘abc’] |
\Z | 从字符串的结束处匹配,如果存在换行,只匹配到换行前的结束字符串,Z是字母里的末尾,用于指示结束处 | re.findall(“oo\w\Z”,“ood123foozaoob”) | [‘oob’] |
^ | 匹配开头,只有后面跟的字符串在开头,才能匹配上 | re.findall(“^alexsel”,“alexselgtaassiqialexsel124”) | [‘alexsel’] |
$ | 匹配末尾,只有它前面的字符串在检测的字符串的最后,才能匹配上 | re.findall(“alexsel$”,“alexselgtaassiqialexsel”) | [‘alexsel’] |
re.findall("a[.]d","aaaacd")
result:
[]
字符 | 含义 | 举例 | 结果 |
---|---|---|---|
[-] | 说明匹配字符范围,如[a-z]表示a到z的字符中的任意一个 | re.findall(“[a-d]\d”, “aaaacd34”) | [‘d3’] |
[^] | 匹配[]除了后面所跟范围的字符,(^在这里有 非 的意思) | re.findall(“[^1-4]\w”,“aaazz1111344444c446”) | [‘aa’, ‘az’, ‘z1’, ‘c4’], |
字符 | 功能 |
---|---|
(abc) | 将括号中字符作为一个分组 |
(|) | 匹配左右任意一个表达式 |
(\num) | 引用分组num |
(?P) | 分组取别名 |
(?P=name) | 引用别名为name的分组 |
取名字格式:(?P<name>pattern)
引用格式:(?P=name)-,不必再详细描述pattern
如果要取得该捕获组的内容,可以.group("name")
# 需要找到text/javascript和//icws.jb51.net/good2021/arc2019.js的内容
import re
html = """<script type="text/javascript" src='//icws.jb51.net/good2021/arc2019.js'></script>"""
result = re.search(r"<(\w+) type=(.+) src=(.+)></\1>", html)
r2 = result.group(2)
r3 = result.group(3)
print(result)
print(r2, r3)
result:
<re.Match object; span=(0, 82), match='<script type="text/javascript" src=\'//icws.jb51.>
"text/javascript" '//icws.jb51.net/good2021/arc2019.js'
# 捕获组应用,(?P<name1>\w+)给正则表达式的子组取名字,后面(?P=name1)直接使用,而不用再详细描述。
import re
html = "<html><h1>Shanghai</h1></html>"
result = re.search("<(?P<name1>\w+)><(?P<name2>\w+)>(.+)</(?P=name2)></(?P=name1)>", html)
r3 = result.group(3)
print(result)
print(r3)
result:
<re.Match object; span=(0, 30), match='<html><h1>Shanghai</h1></html>'>
Shanghai
re.match(pattern, string, flags=0)
参数 | 描述 |
---|---|
pattern | 匹配的正则表达式 |
string | 要匹配的字符串 |
flags | 标志位,用于控制正则表达式的匹配方式。如:是否区分大小写,多行匹配等等。 |
参数 | 描述 |
---|---|
re.I | 忽略大小写 |
re.L | 表示特殊字符集 \w, \W, \b, \B, \s, \S 依赖于当前环境 |
re.M | 多行模式 |
re.S | 即为 . 并且包括换行符在内的任意字符(. 不包括换行符) |
re.U | 表示特殊字符集 \w, \W, \b, \B, \d, \D, \s, \S 依赖于 Unicode 字符属性数据库 |
re.X | 为了增加可读性,忽略空格和 # 后面的注释 |
匹配对象方法 | 描述 |
---|---|
group(num=0) | 分组捕获,匹配的整个表达式的字符串,group() 可以一次输入多个组号,在这种情况下它将返回一个包含那些组所对应值的元组 |
groups() | 返回一个包含所有小组字符串的元组,从1到 所含的小组号 |
span() | 返回匹配到内容的下标范围,元组形式 |
start() | 返回匹配到内容的开始位置 |
end() | 返回匹配到内容的结束位置 |
groupdict() | 将命名后的子组以字典形式返回 |
import re
result =re.match("oo\w{10}","ood123foozaoob")
print(result)
print(result.group())
result:
<re.Match object; span=(0, 12), match='ood123foozao'>
ood123foozao
code: import re line = "Cats are smarter than dogs" match_obj = re.match(r"(?P<first>.*) are (?P<second>.*?) (?P<third>.{2})", line, re.M | re.I) if match_obj: print("match_obj.group() : ", match_obj.group()) print("match_obj.group(1) : ", match_obj.group(1)) print("match_obj.group(2) : ", match_obj.group(2)) print("match_obj.group(3) : ", match_obj.group(3)) print(match_obj.groupdict()) print(match_obj.groups()) else: print("No match!!") result: match_obj.group() : Cats are smarter th match_obj.group(1) : Cats match_obj.group(2) : smarter match_obj.group(3) : th {'first': 'Cats', 'second': 'smarter', 'third': 'th'} ('Cats', 'smarter', 'th')
re.search(pattern, string, flags=0)
code: import re line = "Cats123are45smarter78than<>dogs" search_obj = re.search(r"(?P<first>\d{2})are(?P<second>.+)(?P<third>.{2})", line, re.M | re.I) if search_obj: print("search_obj.group() : ", search_obj.group()) print("search_obj.group(1) : ", search_obj.group(1)) print("search_obj.group(2) : ", search_obj.group(2)) print("search_obj.group(3) : ", search_obj.group(3)) print(search_obj.groupdict()) else: print("No match!!") result: search_obj.group() : 23are45smarter78than<>dogs search_obj.group(1) : 23 search_obj.group(2) : 45smarter78than<>do search_obj.group(3) : gs {'first': '23', 'second': '45smarter78than<>do', 'third': 'gs'}
re.findall(pattern, string, flags=0)
import re
text = "https://mp.csdn.net/postedit/828posd65219"
result = re.findall(r"pos[a-z]+", text)
print(result)
result:
['postedit', 'posd']
import re
result = re.findall(r'(\w+)=(\d+)', 'set width=20 and height=10')
print(result)
result:
返回元组列表,元组里是分组的各项内容
[('width', '20'), ('height', '10')]
import re
string = "abcdefg acbdgef fedcfe cadbgfe"
result0 = re.findall("\w+\s+\w+",string)
result1 = re.findall("(\w+)\s+\w+",string)
result2 = re.findall("(\w+)\s+(\w+)",string)
print(result0)
print(result1)
print(result2)
result:
['abcdefg acbdgef', 'fedcfe cadbgfe']
['abcdefg', 'fedcfe'] #带有一个圆括号,输出括号内匹配的内容
[('abcdefg', 'acbdgef'), ('fedcfe', 'cadbgfe')] #带有2个圆括号,输出是list,list中的元素是元组,元组的内容是圆括号匹配的内容
re.finditer(pattern, string, flags=0)
import re
result = re.finditer(r"\d+\w?", "12a32bc43jf3")
print(result)
print(result.__next__())
print(result.__next__())
for i_result in result:
print(i_result.group())
result:
<callable_iterator object at 0x000002EE5A2D6E48>
<re.Match object; span=(0, 3), match='12a'>
<re.Match object; span=(3, 6), match='32b'>
43j
3
re.sub(pattern, repl, string, count=0, flags=0)
参数 | 描述 |
---|---|
pattern | 正则中的模式字符串 |
repl | 替换的字符串,也可为一个函数,如果是函数的时候,将match对象传给它,返回一个字符串 |
string | 要被查找替换的原始字符串 |
count | 模式匹配后替换的最大次数,默认 0 表示替换所有的匹配 |
flags | 标志位,用于控制正则表达式的匹配方式。如:是否区分大小写,多行匹配等 |
import re
phone = "2004-959-559 # 这是一个国外电话号码"
# 删除字符串中的 Python注释和-
num1 = re.sub(r'-|#|\s.*$', "", phone, 2)
print("电话号码是: ", num1)
num2 = re.sub(r'-|#|\s.*$', "", phone)
print("电话号码是: ", num2)
result:
电话号码是: 2004959559 # 这是一个国外电话号码
电话号码是: 2004959559
# 为匹配到的数字做加20操作
import re
def func(obj_match):
result = int(obj_match.group()) + 20
return str(result)
score = "Math:90, English:30"
num1 = re.sub(r"\d+", func, score)
print("作弊成绩是: ", num1)
result:
作弊成绩是: Math:110, English:50
import re
phone = "2004-959-559 # 这是一个国外电话号码"
# 删除字符串中的 Python注释和-
num1 = re.subn(r'-|#|\s.*$', "", phone, 2)
print("电话号码是: ", num1)
num2 = re.subn(r'-|#|\s.*$', "", phone)
print("电话号码是: ", num2)
result:
电话号码是: ('2004959559 # 这是一个国外电话号码', 2)
电话号码是: ('2004959559 ', 3)
re.split(pattern, string[, maxsplit=0, flags=0])
import re
phone = "2004-959-559 # 这是一个国外电话号码"
# 以字符串中的-和#为分割标志,将字符串分割为几部分,形成列表。
result1 = re.split(r'-|#', phone)
print(result1)
result2 = re.split(r'-|#', phone, 2) #最多分割2次
print(result2)
result3 = re.split(r'\d(-|#)', phone)
print(result3)
result:
['2004', '959', '559 ', ' 这是一个国外电话号码']
['2004', '959', '559 # 这是一个国外电话号码']
['200', '-', '95', '-', '559 # 这是一个国外电话号码']
# 匹配出hello以及后面的数字。 code: import re msg = "hello123456hello" result1 = re.search("hello\d+", msg) result2 = re.search("hello\d+?", msg) # + 匹配1个或无穷,因为加了?则只匹配1个数字 result3 = re.search("hello\d*?", msg) # + 匹配0个或无穷,因为加了?则只匹配0个数字 print(result1.group()) print(result2.group()) print(result3.group()) result: hello123456 hello1 hello
import re
phone = "15800458778"
# 以字符串中的-和#为分割标志,将字符串分割为几部分,形成列表。
result1 = re.match("[1]\d{9}[^47]$",phone) # [^47]非4非7
#result1 = re.match("[1]\d{9}[0-35-689]$",phone)
print(result1)
result:
<re.Match object; span=(0, 11), match='15800458778'>
# 从网上爬一个图片下来
import re
import requests
html = """<img class="currentImg" id="currentImg" οnlοad="alog && alog('speed.set', 'c_firstPageComplete', +new Date); alog.fire && alog.fire('mark');" src="https://gimg2.baidu.com/image_search/src=http%3A%2F%2Fb-ssl.duitang.com%2Fuploads%2Fblog%2F201412%2F30%2F20141230224715_dQsxN.jpeg&refer=http%3A%2F%2Fb-ssl.duitang.com&app=2002&size=f9999,10000&q=a80&n=0&g=0n&fmt=auto?sec=1654769430&t=7ada52c1cff9fd86d63eb311de170c7e" width="210.36168132942" height="269" style="top: 0px; left: 89px; width: 310px; height: 465px; cursor: pointer; display: block;" log-rightclick="p=5.102" title="点击查看图片来源">"""
result = re.search(r'.*src="(.+?)"', html)
image_path = result.group(1)
req = requests.get(image_path)
with open("chenxiao.jpg", "wb") as fs:
fs.write(req.content)
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。