2022年 11月 4日

python中的正则表达式

正则表达式简称‘regex’,是文本模式的描述方式。

Python中的正则表达式的函数均在re模块中,使用正则表达式需要:

import re

1.正则表达式中的方法

  1. import re
  2. color=re.compile(r'.色')#r为原始字符串,表示忽略转义,纯文本
  3. mo=color.search('苹果是红色')
  4. print(mo.group())#红色

向re.compile()方法传入一个字符串值,表示正则表达式,它将返回一个Regex模式对象

search()方法将返回一个Match对象,包含被查找字符串的“第一次”匹配的文本

  1. import re
  2. phoneNum=re.compile(r'\d\d\d-\d\d\d-\d\d\d\d')
  3. phoneNum.findall('Cell:415-555-9999 Work:212-542-0000')
  4. print(phoneNum.findall)#[('415'),('555'),('9999'),('212'),('542'),('0000')]

findall()方法将返回一组字符串,包含被查找字符串中的“所有”匹配文本

无分组-findall()方法不是返回一个Match对象,而是返回一个字符串列表,列表的每个字符串都是一段被查找的文本,它匹配该正则表达式

有分组-findall()方法将返回元组的列表。每个元组表示一个找到的匹配,其中的项就是正则表达式中每个分组的匹配字符串

2.正则表达式匹配多种模式

2.1点-匹配所以字符

.表示要匹配除了换行符之外的任何单个字符

2.2星号-重复匹配任意次

*表示匹配前面的子表达式任意次,包括0次

.*-紧跟在.后面,表示任意字符可以出现任意次

*前面不一定是点,也可以是其他字符

  1. import re
  2. name=re.compile(r'First Name:(.*) Last Name:(.*)')
  3. mo=name.search('First Name: AI Last Name: Smith')
  4. print(name.group(0))#'AI'
  5. print(name.group(1))#'Smith'

注意:

点-星使用贪心模式:它总是匹配尽可能多的文本。要用“费贪心”模式匹配所以的文本,就要使用点-星和问号,像和大括号一起使用时那样,问号告诉Python使用分贪心模式匹配(贪心模式和非贪心模式会在后文讲解)

2.3加号-重复匹配多次

+表示匹配前面的子表达式一次或多次,但不包括0次

用法和*类似,但是*可以为0次,+至少为1次

星号不要求分组出现在匹配的字符串中,但加号不同,加号前面的分组必须至少出现一次

2.4花括号-匹配指定次数

花括号表示前面的字符匹配指定的次数,就在正则表达式中该分组的后面跟上花括号包围的数字

eg.

(Ha){3}将匹配字符串”HaHaHa”

除了一个数字,还可以指定一个范围,即花括号中写下一个最小值,一个括号和一个最大值

也可以不写花括号中的第一个或第二个数字,表示不限定最大值或最小值,eg

(ha){3,4}匹配’hahaha’,’hahahaha’和’hahahahaha’

(ha){0,5}将匹配0-5次实例

2.5贪心和非贪心匹配

Python中的正则表达式默认是‘贪心’的,这表示在有二义的情况下,它们尽可能匹配最长的字符串。花括号的非“贪心”版本尽可能匹配最短的字符串,即在结束的花括号后面跟着一个问号

  1. import re
  2. greed=re.compile(r'(Ha){3,5}')
  3. mo=greed.search('HaHaHaHaHa')
  4. print(greed.group())#'HaHaHaHaHa'
  5. greed=re.compile(r'(Ha){3,5}?')
  6. mo=greed.search('HaHaHaHaHa')
  7. print(greed.group())#'HaHaHa'

问号在正则表达式中有两种含义:声明非贪心匹配或表示可选的分组

2.6对元字符的转义

反斜杠\在正则表达式中有多种用途

如果我们要搜索的内容本身就包含元字符,就开以使用反斜杠进行转义

匹配某种字符类型:

   反斜杠后面接一些字符,表示匹配某种类型的一个字符

\d 表示0-9的任意一个数字
\D 表示除了0-9的任意字符
\s 匹配任意一个空白字符,空格,tab,换行符等
\S 匹配任意一个非空白字符
\w 匹配任意一个文字字符,大小写字母,数字,下划线等
\W 匹配任意一个非文字字符

2.7方括号-匹配某几种类型

方括号表示要匹配某几种类型的字符

eg.[abc]可以匹配a,b,c中的任意一个字符。相当于[a-c]

反斜杠也可以用在方括号里面,比如[\s,.]表示匹配任何空白字符,或逗号,或点

一些元字符在方括号中变得和普通字符一样了

eg[ab1.]匹配a,b,1,.中的任意一个字符

这里的.在括号里面不在表示匹配任意字符了,而就是表示.这个字符

2.8^的用法

^表示匹配文本的起始位置

如果是多行模式,表示匹配文本每行的开头位置

如果在方括号中使用^,表示非方括号里面的字符集和

eg[^1-9]表示除了1到9的任意字符的集合

2.9起始,结束位置和单行,多行模式

^表示匹配文本的起始位置

正则表达式可以设定单行模式和多行模式#Python默认为单行模式

如果是单行模式,表示匹配整个文本的开头位置

如果是多行模式,表示匹配整个文本每行的开头位置

如果想使用多行模式可以添加re.M

eg  p=re.compile(r’^\d+’,re.M)#转换为多行模式

$表示匹配文本的结束位置

    表示该字符串必须以这个正则表达式的模式结束

    可以同时使用^和$,表明整个字符串必须匹配该模式,也就是说,只匹配该字符串的摸个子集是不够的

    单行模式时表示整个文本的最后

2.10括号-组选择

括号称之为正则表达式的组选择。是从正则表达式匹配的内容里面扣取出其中的某些部分

  1. import re
  2. p=re.compile(r'^(.*)',re.M)#组选择,所得文本不包含括号
  3. for i in p.findall(content):
  4. print(i)#多组返回元素,每个组是元组中的一个元素

2.11问号-匹配0-1次

?表示前面的子表达式0次或1次

2.12使用正则表达式切割字符串

字符串对象的split()方法只适用于非常简单的字符串分割情形。需要灵活的切割字符串的时候,就不好用了。

如果提取的字符串有的是分号隔开,有的是逗号隔开,有的是空格隔开,而且分割的符号周围还有不定数量的空格,这时最好使用正则表达式里面的split方法:

  1. names='关羽;张飞,赵云,马超, 黄忠 李逵'#这时最好使用正则表达式中的split方法
  2. import re
  3. namelist=re.split(r'[;,\s]\s*',names)
  4. print(namelist)

正则表达式[;,\s]\s*指定了分隔符为分号,逗号,空格里面的任意一种均可,并且该符号周围可以有不定数量的空格

2.13指定替换函数

正则表达式不仅能找到文本模式,而且能够用新的文本替换这些模式。Regex对象的sub()方法需要传入俩个参数

第一个参数是一个字符串,用于替换发现的匹配。第二个参数是一个字符串,即正则表达式sub()方法返回替换完成后的字符串

匹配边界

字符 功能
^ 匹配字符串开头
$ 匹配字符串结尾
\b 匹配一个单词的边界
\B 匹配非单词的边界

匹配分组

字符 功能
| 匹配左右任意一个表达式
(ab) 将括号中字符作为一个分组
\num 引用分组num匹配到的字符串
(?p<name>) 分组起别名
(?p=name) 引用别名为name分组匹配到的字符串

本作者为初学者,如用错误请读者指出