【Python进阶必备】一文掌握re库:实战正则表达式

目录

re库初识

re库基础使用方法

compile()函数

基本用法

正则表达式常用规则字符

match与search方法

match

search

match/search

findall与finditer方法

使用findall()返回所有匹配项

使用findall()提取多个组的匹配

使用finditer()逐个返回Match对象

使用finditer()并处理复杂匹配结构

进阶用法

分组与反向引用

替换文本中的部分内容

提取并重组子组

在搜索结果中使用子组

贪婪与懒惰匹配

预定义字符集与特殊字符

结语与讨论


亲爱的读者,你是否在编程过程中遇到过字符串处理难题?是否对繁琐复杂的文本匹配操作感到困扰?今天,我们就一起深入探索Python世界中的强大工具——re模块,它是Python标准库中用于处理正则表达式的利器,帮你轻松驾驭各类字符串处理任务。

re库初识

Python的re模块提供了完整的正则表达式功能。正则表达式(Regular Expression)是一种强大的文本模式匹配工具,它能高效地进行查找、替换、分割等复杂字符串操作。

在Python中,通过 import re 即可引入这一神器。 


re库基础使用方法

compile()函数

首先,我们需要使用re.compile()函数将正则表达式编译为Pattern对象

基本用法

import re# 匹配一个或多个连续的数字字符
pattern = re.compile(r'\d+') # 匹配email电邮地址
email_pattern = re.compile(r'\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}\b', re.IGNORECASE)# 匹配任意字母数字组成的用户名(至少1个字符)
username_pattern = re.compile(r'\w+')# 匹配任意URL链接
url_pattern = re.compile(r'http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\\(\\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+')# 匹配电话号码(格式如:123-456-7890 或 (123) 456-7890)
phone_pattern = re.compile(r'(\d{3}[-\.\s]??\d{3}[-\.\s]??\d{4}|\(\d{3}\)\s*\d{3}[-\.\s]??\d{4})')# 匹配IPv4地址
ipv4_pattern = re.compile(r'(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)')# 匹配信用卡号(一般为16位数字,可能包含空格分隔符)
credit_card_pattern = re.compile(r'\d{4}[- ]?\d{4}[- ]?\d{4}[- ]?\d{4}')# 匹配日期格式(YYYY-MM-DD)
date_pattern = re.compile(r'\d{4}-\d{2}-\d{2}')# 匹配颜色代码(如 #FF0000)
color_code_pattern = re.compile(r'^#([A-Fa-f0-9]{6}|[A-Fa-f0-9]{3})$')# 匹配整数和小数(包括负数、正数和零)
number_pattern = re.compile(r'-?\d+(\.\d+)?')

正则表达式常用规则字符

  • \d:在大多数正则表达式语法中(包括Python中的 re 模块),\d 相当于 [0-9],即它会匹配任意一个十进制数字字符,相当于阿拉伯数字从0到9。
  • +:这是一个量词,表示前面的元素(这里是\d)至少出现一次或多次。因此,\d+ 作为一个整体,它会匹配一个或连续的一个以上数字字符,例如 "123"、"456789" 等等。

  • \w:匹配字母(大写或小写)、数字和下划线(等价于 [a-zA-Z0-9_])。

  • \s:匹配任何空白字符,包括空格、制表符、换行符等。
  • . (句点):匹配除换行符之外的任何单个字符。
  • ^:在字符串起始位置时匹配,或者在字符类 [] 中表示反向选择(如 [^abc] 匹配非 a、b、c 的字符)。
  • $:在字符串结束位置时匹配。
  • *:零次或多次匹配前面的元素。
  • ?:零次或一次匹配前面的元素。
  • {m,n}:前面的元素至少出现 m 次,至多出现 n 次。
  • |:表示“或”操作,用于匹配多个选项之一。
  • ():用于分组和捕获子匹配项。

re.compile(pattern, flags=0) 的作用是:

  1. 预编译:将正则表达式转换为编译过的模式对象,提高后续匹配操作的速度。
  2. 复用:创建一次编译好的模式后,可以在程序的不同地方重复使用该模式进行匹配、查找、替换等操作。
  3. 支持标志:可以传递标志参数来改变正则表达式的默认行为,如忽略大小写、多行模式等。

match与search方法

pattern.match()方法只检测字符串开始位置是否满足匹配条件;而pattern.search()方法会搜索整个字符串以找到第一个匹配项。

match

import retext = "2023-01-01 This is a date at the start of the string."# 使用match()方法,只从字符串开始位置匹配日期格式
pattern = re.compile(r'\d{4}-\d{2}-\d{2}')
match_result = pattern.match(text)if match_result:print(f"Match found: {match_result.group(0)}")
else:print("No match at the beginning of the string.")# 输出:
# Match found: 2023-01-01
import retext = "The date today is 2023-01-01, let's remember it."# 使用search()方法在整个字符串中搜索日期格式
pattern = re.compile(r'\d{4}-\d{2}-\d{2}')
search_result = pattern.search(text)if search_result:print(f"Search found: {search_result.group(0)}")
else:print("No match found in the string.")# 输出:
# Search found: 2023-01-01

match/search

import retext = "This sentence does not start with a date like 2023-01-01."# match()不会找到任何匹配项,因为日期不在字符串开头
match_result = re.match(r'\d{4}-\d{2}-\d{2}', text)
if match_result:print("Match found.")
else:print("No match at the beginning using match().")# search()能找到匹配项,因为它搜索整个字符串
search_result = re.search(r'\d{4}-\d{2}-\d{2}', text)
if search_result:print("Search found.")
else:print("No match found anywhere using search().")# 输出:
# No match at the beginning using match().
# Search found.

findall与finditer方法

pattern.findall()返回所有非重叠匹配结果的列表;pattern.finditer()返回一个迭代器,逐个返回Match对象。

使用findall()返回所有匹配项

import retext = "The3 quick5 brown5 fox3 jumps5 over4 the3 lazy4 dog."# 找到文本中所有的"fox"
pattern = re.compile(r'\d+')
matches = pattern.findall(text)print(matches)# 输出: ['3', '5', '5', '3', '5', '4', '3', '4']

使用findall()提取多个组的匹配

import retext = "John Doe, Jane Smith, Alice Johnson"# 提取所有名字和姓氏
pattern = re.compile(r'(\w+) (\w+)')
matches = pattern.findall(text)print(matches)# 输出: [('John', 'Doe'), ('Jane', 'Smith'), ('Alice', 'Johnson')]# 返回的是元组组成的列表,每个元组代表一个匹配的结果,其中包含了括号分组的内容

使用finditer()逐个返回Match对象

import retext = "I have 3 apples and 7 bananas in 2 baskets."# 查找所有数字
pattern = re.compile(r'\d+')for match in pattern.finditer(text):print(match.group(0))# 输出:
# 3
# 7
# 2
# finditer()方法逐个返回Match对象,并可以通过group()方法获取匹配的具体内容

使用finditer()并处理复杂匹配结构

import retext = "colors: red, colors:blue; shapes: square, shapes:circle"# 匹配颜色或形状
pattern = re.compile(r'(?:colors?[:\s]+(\w+)(?:[,;\s]|$))|(?:shapes?[:\s]+(\w+)(?:[,;\s]|$))')for match in pattern.finditer(text):if match.group(1):  # 如果是颜色print(f"Color found: {match.group(1)}")elif match.group(2):  # 如果是形状print(f"Shape found: {match.group(2)}")# 输出:
# Color found: red
# Color found: blue
# Shape found: square
# Shape found: circle

进阶用法

分组与反向引用

通过圆括号可以创建子组,以便捕获和引用部分匹配内容。如re.compile(r'(\w+) (\d+)')\1\2分别代表第一个和第二个子组的内容。

替换文本中的部分内容

import retext = "John Doe has 3 apples and Jane Smith has 7 bananas."
pattern = re.compile(r'(\w+) (\d+)')
new_text = pattern.sub(r'\1 has \2 fruits', text)print(new_text)
# 输出: "John Doe has 3 fruits and Jane Smith has 7 fruits."# 在这个例子中,\1 替换为第一个子组(名字),\2 替换为第二个子组(数字)

提取并重组子组

import retext = "The date is 2023-01-01, and the time is 15:30:45."
pattern = re.compile(r'(\d{4})-(\d{2})-(\d{2})')match = pattern.search(text)
if match:date_reformatted = f"{match.group(1)}.{match.group(2)}.{match.group(3)}"print(date_reformatted)# 输出: "2023.01.01"# 这里直接通过group()方法获取每个子组的内容,并重新组合

在搜索结果中使用子组

import retext = "Some emails are user1@exam.com, user2@apple.net, and user3@example.org."
pattern = re.compile(r'([\w.%+-]+)@([\w.-]+)\.([a-z]{2,})')matches = pattern.findall(text)
for email in matches:username, domain, dtype = email[0], email[1], email[2]print(f"Username: {username}, Domain: {domain}.{dtype}")# 使用子组匹配的邮箱用户名和域名# 输出:# Username: user1, Domain: exam.com# Username: user2, Domain: apple.net# Username: user3, Domain: example.org

贪婪与懒惰匹配

*+?后添加?可变为非贪婪模式,尽可能少地匹配字符。

贪婪与非贪婪的 * 量词

import retext = "I love Python programming and Java programming very much!"# 贪婪模式
pattern_greedy = re.compile(r'love.*programming')
match_greedy = pattern_greedy.search(text)
print(match_greedy.group(0))  # 输出: 'love Python programming and Java programming'# 非贪婪模式
pattern_lazy = re.compile(r'love.*?programming')
match_lazy = pattern_lazy.search(text)
print(match_lazy.group(0))  # 输出: 'love Python programming'

贪婪与非贪婪的 + 量词

import retext = "The numbers are 139-626 and 123456."# 贪婪模式
pattern_greedy = re.compile(r'\d+')
matches_greedy = pattern_greedy.findall(text)
print(matches_greedy)
# 输出: ['139', '626', '123456']# 非贪婪模式
pattern_lazy = re.compile(r'\d+?')
matches_lazy = pattern_lazy.findall(text)
print(matches_lazy)
# 输出: ['1', '3', '9', '6', '2', '6', '1', '2', '3', '4', '5', '6']

 贪婪与非贪婪的 ? 量词

import retext = "Optional text or not?"# 贪婪模式
pattern_greedy = re.compile(r'(Optional)?.*')
match_greedy = pattern_greedy.search(text)
print(match_greedy.group(0))  # 输出: 'Optional text or not?'# 非贪婪模式
pattern_lazy = re.compile(r'(Optional)?.*?')
match_lazy = pattern_lazy.search(text)
print(match_lazy.group(0))  # 输出: 'Optional'

预定义字符集与特殊字符

\d\D\w\W\s\S分别代表数字、非数字、单词字符、非单词字符、空白符、非空白符。


结语与讨论

正则表达式和re库的强大远不止于此,其深度和灵活性足以应对各种复杂的文本处理场景。然而,掌握好这门艺术需要不断的实践和积累,本文只是带你踏入了Python re库的门槛,但正则表达式的奥秘还等待着你进一步挖掘。实践中如果遇到“明明规则写得对,为何匹配不上?”这类疑问,不妨回看本文,或是在留言区留下你的问题,我们一同探讨解惑,让正则表达式真正成为你手中的“文本魔法棒”。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/236316.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Realm Management Extension领域管理扩展之系统架构

RME不仅仅是一组处理器功能,为了充分利用RME引入的功能,系统的其余部分需要提供支持。 下图显示了一个示例系统以及引入RME后受到影响的组件: 主存储器保护 RME启用的系统包括内存加密和可能的完整性。基线加密要求支持对外部内存进行加密,使用每个PA空间的单独加密密钥或…

3. SPSS数据文件的基本加工和处理

如何获取SPSS自带的案例数据文件? 首先找到SPSS的安装目录,然后找到Samples文件夹 可以看到有不同语言版本,选择简体中文 就能看到很多.sav文件 数据文件的整理 个案排序 单值排序 例:对于下面的数据集,将工资按…

访问学者申请需要注意什么?

访问学者申请是一项复杂而重要的过程,需要申请人在准备材料和过程中注意一些关键事项,以确保顺利完成申请并提高成功率。以下是知识人网小编的一些建议,希望对你的访问学者申请有所帮助。 1. 详细了解目标学术机构: 在申请访问学…

使用curl命令在Linux上进行HTTP请求

在Linux系统中,curl是一个非常强大的命令行工具,用于发送各种类型的HTTP请求。通过简单的命令,你可以发送GET、POST、PUT、DELETE等请求,以及设置请求头、处理响应等。以下是一些使用curl进行HTTP请求的常见用法和示例。 1. 发送…

二极管选型怎么选?常用参数要熟练~

同学们大家好,今天我们继续学习杨欣的《电子设计从零开始》,这本书从基本原理出发,知识点遍及无线电通讯、仪器设计、三极管电路、集成电路、传感器、数字电路基础、单片机及应用实例,可以说是全面系统地介绍了电子设计所需的知识…

Visual Studio 2019 ctrl+f 呼出查找和替换窗口

有时候 ctrlshiftf 呼出查找和替换窗口不起作用,可能和其它程序的快捷键冲突,解决方案: ------------英文版本------------ 依次点击VS菜单栏中的 Tools - Options - Environment - Keyboard: 1. 在右侧的 Show commands containing: 文本框输…

实战使用工具appuploader上线发布苹果商店

实战使用工具appuploader上线发布苹果商店 我们发布ios应用的时候,步骤繁琐,非常耗时,appuploader工具就是解决一站式从上传到发布到appstore应用商店的,当我们开发完app后,需要将ipa/apk提交给测试人员测试&#xff0…

软件测试进阶自动化测试流程

如果想让测试在公司的项目中发挥出它最大的价值,并不是招两个测试技术高手,或引入几个测试技术,而是测试技术对项目流程的渗透,以及测试流程的改进与完善。虽然,当然测试行业前景乐观,许多中小企业也都在引…

【算法Hot100系列】有效的数独

💝💝💝欢迎来到我的博客,很高兴能够在这里和您见面!希望您在这里可以感受到一份轻松愉快的氛围,不仅可以获得有趣的内容和知识,也可以畅所欲言、分享您的想法和见解。 推荐:kwan 的首页,持续学习,不断总结,共同进步,活到老学到老导航 檀越剑指大厂系列:全面总结 jav…

解决数据库事务问题的Java神奇之道: 构建高效、可靠和灵活的事务管理系统

目录 1、前言 2、数据库事务基础知识 2.1 事务的定义与特性 2.2 数据库事务隔离级别 2.3 事务的并发控制与恢复 2.4 事务管理的重要性 3、传统的事务管理方式 3.1 基于JDBC的事务管理 3.1.1 基本概念和API介绍 3.1.2 事务的隔离级别控制 3.1.3 事务的异常处理与回滚…

MySQL 8查询语句之查询所有字段、特定字段、去除重复字段、Where判断条件

《MySQL 8创建数据库、数据表、插入数据并且查询数据》里边有我使用到的数据。 再使用下方的语句补充一些数据: insert into Bookbought.bookuser(id,username,userphone,userage,sex,userpassword) values (11,Book Break,22245678911,18,male,good#111); insert…

Simpy简介:python仿真模拟库-03/5

一、说明 在过去的两篇文章中,我们了解了 simpy 的基础知识、声明变量和处理表达式。值得注意的例子包括评估导数和积分。现在,让我们继续使用函数。 二、SymPy — 函数类 SymPy 包包含 sympy.core.function 模块中的 Function 类。该类作为各种数学函数…

计算机网络面试八股复习:常见的Http状态码

前言 面试被问到过一次。自己最近使用Gin框架,在Response的时候有时候也会用到一个自定义的状态码。因此归纳一下这方面,供自己日后面试复习以及开发时候参考。 HTTP 全名“超文本传输协议”(我也不懂为什么面试官问这个…) 属…

关于自动化测试用例失败重试的一些思考

动化测试用例失败重跑有助于提高自动化用例的稳定性,那我们来看一下,python和java生态里都有哪些具体做法? 怎么做 如果是在python生态里,用pytest做测试驱动,那么可以通过pytest的插件pytest-rerunfailures来实现失…

2023年全球软件质量效能大会(QECon上海站):核心内容与学习收获(附大会核心PPT下载)

会议聚焦于软件质量和效能的提升。在智能时代,随着数字化的深入人心,软件正在随着云计算、移动互联网、物联网等的发展而不断进化,软件对企业的发展愈加重要,大家对软件的质量要求也在从传统功能、性能、安全这些基础层面向着用户…

水产冷链物流行业零下25℃库架一体 海格里斯HEGERLS四向穿梭式冷藏冷库智能密集仓

随着国内外仓储物流整体规模和低温产品消费需求的稳步增长,冷链市场应用潜力不断释放。在传统“货架叉车”的方式下,货物、人员及机械设备不断进出,容易造成温度波动,导致冷量流失。立体冷库则以更高密度、更具成本效益的方式&…

Unity URP下阴影锯齿

1.概述 在Unity开发的URP项目中出现阴影有明显锯齿。如下图所示: 并且在主光源的Shadow Type已经是Soft Shadows模式了。 2.URP Asset 阴影出现锯齿说明阴影质量不高,所以要先找到URP Asset文件进行阴影质量参数的设置。 1.打开PlayerSetting找到Graph…

对于软件测试的认识和了解

对软件测试的认识: 软件测试要求开发人员避免测试自己开发的程序。从心理学角度讲,这是很有道理的。特别是一个相对复杂的系统,开发人员在刚刚开发完成的时候,尚沉浸于对自己设计的回味之中。此时去测试的话往往会侧重于程序本身的…

【设计模式-6】建造者模式的实现与框架中的应用

建造者模式又被成为生成器模式,是一种使用频率比较低,相对复杂的创建型模式,在很多源码框架中可以看到建造者的使用场景,稍后我们会在本文末尾展示几个框架的使用案例。  建造者模式所构造的对象通常是比较复杂而且庞大的&#x…

turnjs实现翻书效果

需求:要做一个效果,类似于阅读器上的翻书效果。 咱们要实现这个需求就需要使用turnjs这个插件,他的官网是turnjs官网。 进入官网后可以点击 这个按钮去下载官网的demo。 这个插件依赖于jQuery,所以你的先安装jQuery. npm insta…