正则表达式

正则表达式

Posted by BY on September 2, 2021

正则表达式

作用:

在实际开发过程中经常会有查找符合某些复杂规则的字符串的需要,比如:邮箱、图片地址、手机号码等,这时候想匹配或者查找符合某些规则的字符串就可以使用正则表达式了。

概念:

正则表达式就是记录文本规则的代码。对字符串操作的一种匹配公式。

特点:
  • 正则表达式的语法很令人头疼,可读性差
  • 正则表达式通用性很强,能够适用于很多编程语言

re的模块介绍

在Python中需要通过正则表达式对字符串进行匹配的时候,可以使用一个 re 模块

使用格式:

导入re模块
import re
match匹配数据
match(正则表达式,要匹配的字符串)
result = re.match(正则表达式,要匹配的字符串)
group提取数据
result.group()
# 导入re模块
import re

# 使用match方法进行匹配操作  match从最开始的地方匹配
result = re.match(正则表达式,要匹配的字符串)

# 如果上一步匹配到数据的话,可以使用group方法来提取数据
result.group()
# 导入re模块
import re

# 使用match方法进行匹配操作  match从最开始的地方匹配
result = re.match('china is', 'china is number one')

# 如果上一步匹配到数据的话,可以使用group方法来提取数据
a = result.group()
print(a)
代码 功能
. 匹配任意一个字符(除了\n)
[] 匹配[]中列举的字符
\d 匹配数字,即0-9.(digit)
\D 匹配非数字,即不是数字。
\s 匹配空白,即空格,tab键.(space)
\S 匹配非空白
\w 匹配非特殊字符,即a-z、A-Z、0-9、_(下划线)、汉字.(word)
\W 匹配特殊字符,即非字母、非数字、非汉字

备注:大写就是对小写功能进行取反。

匹配单个字符
[]: 匹配[]中列举的字符

[]可以连续放多个集合,例如:[a-z0-9A-z]/[ab…z012..9AB…Z]。但是里面不能直接放存储集合的变量

# | []   | 匹配[]中列举的字符 
# 使用match方法进行匹配操作
result = re.match("china[one][one][one]", 'chinaone is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)
else:
    print("没有匹配到")
\d:匹配数字
# | \d   | 匹配数字,即0-9
result = re.match("china\d", 'china1 is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)
else:
    print("没有匹配到")
\D:匹配非数字
# | \d   | 匹配数字,即0-9
result = re.match("china\D", 'china* is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)
else:
    print("没有匹配到")
\s:匹配空格
# | \s   | 匹配空白,即空格,tab键
result = re.match("china\sis", 'china is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
\S:匹配非空格
# | \S   | 匹配非空白
result = re.match("chi\Sa", 'china is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
\w:匹配字符(非特殊字符,包含’_‘、’‘汉字’‘)
# | \w   | 匹配非特殊字符,即a-z、A-Z、0-9、_(下划线)、汉字
result = re.match("chi\wa", 'china is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
\W:匹配非字符(特殊字符)
# | \W   | 匹配特殊字符,即非字母、非数字、非汉字
result = re.match("china\Wis", 'china is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
匹配多个字符
代码 功能
* 匹配前一个字符出现0次或者无限次,即可有可无
+ 匹配前一个字符出现1次或者无限次,即至少有1次
? 匹配前一个字符出现1次或者0次,即要么有1次,要么没有
{m} 匹配前一个字符出现m次
{m,n} 匹配前一个字符出现从m到n次
*:

匹配前一个字符出现0次或者无限次,即可有可无

# china后面可以跟0到无限次数字1-2
result = re.match("china[1-2]*", 'china12123 is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
+:

匹配前一个字符出现1次或者无限次,即至少有1次

# china后面可以跟多个空格
result = re.match("china\s+is", 'china  is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
?:

匹配前一个字符出现1次或者0次,即要么有1次,要么没有

# china后面可以有0-1个数字
result = re.match("china\d?", 'china13 is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
{m}:

匹配前一个字符出现m次

# 当china后面跟2个数字以上,可以查到。
result = re.match("china\d{2}", 'china123 is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
{m,n}:

匹配前一个字符出现从m到n次

# 当china跟两个数字以上,可以查到china带2-3个数字的字符串
result = re.match("china\d{2,3}", 'china12 is number one')
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
匹配开头和结尾

.*可以匹配任意数量的字符

代码 功能
^ 匹配字符串开头
$ 匹配字符串结尾
[^指定字符] 匹配除了指定字符串以外的所有字符(取反操作)
^:

匹配字符串开头

# ^放前面,后跟第一个字符的格式,以下可以查找所有字母开头的字符串
a = 'lixianglong1205@163.com'
result = re.match("^\w.*", a)
# result = re.match("[a-zA-Z0-9]{3,10}", result.group())
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
$:

匹配字符串结尾

# $放在结尾
a = 'lixianglong1205@163.com'
result = re.match(".*\w$", a)
# result = re.match("[a-zA-Z0-9]{3,10}", result.group())
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
以数字为开头,以数字为结尾例子
# 以数字为结尾,以数字为开头
a = 'lixianglong1205@163.com'
result = re.match("^[a-z A-Z].*\w$", a)
# result = re.match("[a-zA-Z0-9]{3,10}", result.group())
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
[^要排除的字符]

要排除的字符,可以列举出来.匹配除了指定字符串以外的所有字符(取反操作)

a = 'lixianglong1205@163.com'
result = re.match("^[a-z A-Z].*[^123456]$", a)
# result = re.match("[a-zA-Z0-9]{3,10}", result.group())
print(result)   # 返回成功了,将返回<re.Match object; span=(0, 5), match='china'>
# 如果上一步匹配到数据的话,可以使用group方法来提取数据
if result:
    a = result.group()
    print(a)    # 输出带空格
    print(len(a))
else:
    print("没有匹配到")
匹配分组
代码 功能
| 匹配左右任意一个表达式
(ab) 将括号中字符作为一个分组
\num 引用分组num匹配到的字符串
(?P<name>) 分组起别名
(?P=name) 引用别名为name分组匹配到的字符串
|:

匹配左右任意一个表达式

import re
# 获取字符串数据
# |匹配左右任意一个表达式
# 水果列表
fruit_list = ["apple", "banana", "orange", "pear"]

# 遍历数据
for value in fruit_list:
    # |    匹配左右任意一个表达式
    match_obj = re.match("apple|pear", value)
    if match_obj:
        print("%s是我想要的" % match_obj.group())
    else:
        print("%s不是我要的" % value)
():

将括号中的字符作为一个分组。可以通过group(下标)来获得分组信息。

import re
# |匹配左右任意一个表达式
# (ab) 将括号中字符作为一个分组.
# |转义字符
match_obj = re.match("[a-zA-Z0-9_]{4,20}@(163|126|qq|sina|yahoo)\.com", "hello@163.com")
if match_obj:
    print(match_obj.group())
    # 获取分组数据
    print("match_obj.group(0)", match_obj.group(0))
    print("match_obj.group(1)", match_obj.group(1))
    # print("match_obj.group(2)", match_obj.group(2))
else:
    print("匹配失败")
import re
# 需求:匹配qq: 10567这样的数据,提取出来qq文字和qq号码
# group(0)代表的是默认匹配多油数据。group(1)-第一个分组的数据;group(2)-第二个分组的数据;
match_obj = re.match("(qq):([1-9]\d{4,10})", "qq:10567")

if match_obj:
    print(match_obj.group())
    # 分组:默认是1一个分组,多个分组从左到右依次加1
    print(match_obj.group(1))
    # 提取第二个分组数据
    print(match_obj.group(2))
else:
    print("匹配失败")
\num:

引用分组num匹配到的字符串

import re
# 需求:匹配出<html>hh</html>

match_obj = re.match("<[a-zA-Z1-6]+>.*</[a-zA-Z1-6]+>", "<html>hh</div>")

if match_obj:
    print(match_obj.group())
else:
    print("匹配失败")
import re
# 需求:匹配出<html><h1>www.itcast.cn</h1></html>
match_obj = re.match("<([a-zA-Z1-6]+)><([a-zA-Z1-6]+)>.*</\\2></\\1>", "<html><h1>www.itcast.cn</h1></html>")

if match_obj:
    print(match_obj.group())
else:
    print("匹配失败")
(?P):

为分组起个别名。

起名:(?P<分组名称>表达式)

使用:(?P=分组名称)–引用别名为name分组匹配到的字符串

import re
# 需求:匹配出<html><h1>www.itcast.cn</h1></html>
match_obj = re.match("<(?P<name1>[a-zA-Z1-6]+)><(?P<name2>[a-zA-Z1-6]+)>.*</(?P=name2)></(?P=name1)>", "<html><h1>www.itcast.cn</h1></html>")

if match_obj:
    print(match_obj.group())
else:
    print("匹配失败")