Python 正则表达式入门(中级篇)
Python 正则表达式入门(中级篇)#
初级篇链接:http://www.cnblogs.com/chuxiuhong/p/5885073.html
上一篇我们说在这一篇里,我们会介绍子表达式,向前向后查找,回溯引用。到这一篇开始前除了回溯引用在一些场合不可替代以外,大部分情况下的正则表达式你应该都会写了。
1.子表达式##
子表达式的概念特别好理解。其实它就是将几个字符的组合形式看做一个大的“字符”。不好理解?举个栗子:我们要匹配类似IP地址这种形式的字符(暂且不考虑数值范围的合理性,这个留作学完之后的思考题吧)。形如192.168.1.1这样的地址我们怎么写表达式呢?
答案一 \d+.?\d+.?\d+.?\d+
不好,一个是太繁琐,另一个是连位数都控制不了
答案二 \d+{1,3}.?\d+{1,3}.?\d+{1,3}.?\d+{1,3}
一般般,复杂但是起码能把位数控制在合理范围
答案三 (\d+{1,3}\.){3}\d+{1,3}\.
利用子表达式,将123.这种数字加小数点看做一个整体字符,对其规定重复匹配的次数,既简洁,效果又好。所以只要你将几个字符组合用圆括号括起来,那么你就可以把一个圆括号内的内容当做一个字符,外面可以加我们之前讲过的所有元字符来控制匹配。
2.向前向后查找##
现在,我们终于来到了向前向后查找这一块。为什么说终于来到这了呢?还记得我们在初级篇最开始的例子吗?
假如你在写一个爬虫,你得到了一个网页的HTML源码。其中有一段html
<html><body><h1>hello world</h1></body></html>
你想要把这个hello world提取出来
import re
key = r"<html><body><h1>hello world</h1></body></html>"#这段是你要匹配的文本
p1 = r"(?<=<h1>).+?(?=</h1>)"#这是我们写的正则表达式规则,你现在可以不理解啥意思
pattern1 = re.compile(p1)#我们在编译这段正则表达式
matcher1 = re.search(pattern1,key)#在源文本中搜索符合正则表达式的部分
print matcher1.group(0)#打印出来
这个正则表达式
p1 = r"(?<=<h1>).+?(?=<h1>)"
看到(?<=<h1>) 和 (?=<h1>)了吗?第一个?<=表示在被匹配字符前必须得有<h1>,后面的?=表示被匹配字符后必须有<h1>
简单来说,就是你要匹配的字符是XX,但必须满足形式是AXXB这样的字符串,那么你就可以这样写正则表达式
p = r"(?<=A)XX(?=B)"
匹配到的字符串就是XX。并且,向前查找向后查找不需要必须同时出现。如果你愿意,可以只写满足一个条件。
所以你也不需要记住哪个是向前查找,哪个是向后查找。只要记住?<=后面跟着的是前缀要求,?=后面跟的是后缀要求。
本质上来说,向前查找和向后查找其实是匹配整个字符串,即AXXB,但返回时仅仅返回一个XX。也就是说,如果你愿意,完全可以避开向前向后查找的方式,直接匹配带有前后缀的字符串,然后做字符串切片处理。
3.回溯引用##
不同于前面的向前向后查找,这一条有时候你未必绕的过去。在有些情况下,你还必须得用到回溯引用,所以你如果想拥有在实际应用中使用正则表达式,回溯引用是你应该了解和掌握的。
我们还是从最开始的例子来说。
你原本要匹配<h1></h1>之间的内容,现在你知道HTML有多级标题,你想把每一级的标题内容都提取出来。你也许会这样写:
p = r"<h[1-6]>.*?</h[1-6]>"
这样一来,你就可以将HTML页面内所有的标题内容全部匹配出来。即<h1></h1>到<h6></h6>的内容都可以被提取出来。但是我们之前说过,写正则表达式困难的不是匹配到想要的内容,而是尽可能的不匹配到不想要的内容。在这个例子中,很有可能你就会被下面这样的用例玩坏。
比方说
<h1>hello world</h3>
发现后面的</h3>了吗?我们不管是怎么写出来这样的标题的,但实实在在的是我们的正则表达式同样会把这里面的hello world匹配出来。这时候就是回溯引用的重要作用。下面就是一个示例:
import re
key = r"<h1>hello world</h3>"
p1 = r"<h([1-6])>.*?</h\1>"
pattern1 = re.compile(p1)
m1 = re.search(pattern1,key)
print m1.group(0)#这里是会报错的,因为匹配不到,你如果将源字符串改成</h1>
结尾就能看出效果
看到\1了吗?原本那个位置应该是[1-6],但是我们写的是\1,我们之前说过,转义符\干的活就是把特殊的字符转成一般的字符,把一般的字符转成特殊字符。普普通通的数字1被转移成什么了呢?在这里1表示第一个子表达式,也就是说,它是动态的,是随着前面第一个子表达式的匹配到的东西而变化的。比方说前面的子表达式内是[1-6],在实际字符串中找到了1,那么后面的\1就是1,如果前面的子表达式在实际字符串中找到了2,那么后面的\1就是2。
类似的,\2,\3,....就代表第二个第三个子表达式。
所以回溯引用是正则表达式内的一个“动态”的正则表达式,让你根据实际的情况变化进行匹配。
中级篇就到这里,其实正则表达式还有很多细节还没有写出来,也有很多元字符我没有交代,但掌握了纲要,懂得原理之后剩下的就类似于查表构造这种活了。
建议看到这的朋友看看《正则表达式必知必会》,初级篇和这篇中有几个例子也是取材于此。
Python 正则表达式入门(中级篇)的更多相关文章
- 转载 Python 正则表达式入门(中级篇)
Python 正则表达式入门(中级篇) 初级篇链接:http://www.cnblogs.com/chuxiuhong/p/5885073.html 上一篇我们说在这一篇里,我们会介绍子表达式,向前向 ...
- Python 正则表达式入门(初级篇)
Python 正则表达式入门(初级篇) 本文主要为没有使用正则表达式经验的新手入门所写. 转载请写明出处 引子 首先说 正则表达式是什么? 正则表达式,又称正规表示式.正规表示法.正规表达式.规则表达 ...
- python正则表达式入门篇
文章来源于:https://www.cnblogs.com/chuxiuhong/p/5885073.html Python 正则表达式入门(初级篇) 本文主要为没有使用正则表达式经验的新手入门所写. ...
- 转载 Python 正则表达式入门(初级篇)
Python 正则表达式入门(初级篇) 本文主要为没有使用正则表达式经验的新手入门所写.转载请写明出处 引子 首先说 正则表达式是什么? 正则表达式,又称正规表示式.正规表示法.正规表达式.规则表达式 ...
- Java正则表达式入门基础篇
正则表达式是一种可以用于模式匹配和替换的规范,一个正则表达式就是由普通的字符(例如字符a到z)以及特殊字符(元字符)组成的文字模式,它 用以描述在查找文字主体时待匹配的一个或多个字符串.正则表达式作为 ...
- python正则表达式入门
基本概念 使用正则表达式需要import re 表达式前加r避免转义 \d代表数字,\s代表空白字符,\w代表字母+数字. .代表任意单个字符 {m,n}代表前面字符至少出现m次,最多出现n次. (x ...
- python爬虫入门---第二篇:获取2019年中国大学排名
我们需要爬取的网站:最好大学网 我们需要爬取的内容即为该网页中的表格部分: 该部分的html关键代码为: 其中整个表的标签为<tbody>标签,每行的标签为<tr>标签,每行中 ...
- python爬虫入门---第一篇:获取某一网页所有超链接
这是一个通过使用requests和BeautifulSoup库,简单爬取网站的所有超链接的小爬虫.有任何问题欢迎留言讨论. import requests from bs4 import Beauti ...
- Python 正则表达式-OK
Python正则表达式入门 一. 正则表达式基础 1.1. 简单介绍 正则表达式并不是Python的一部分. 正则表达式是用于处理字符串的强大工具, 拥有自己独特的语法以及一个独立的处理引擎, 效率上 ...
随机推荐
- Angular2入门系列教程4-服务
上一篇文章 Angular2入门系列教程-多个组件,主从关系 在编程中,我们通常会将数据提供单独分离出来,以免在编写程序的过程中反复复制粘贴数据请求的代码 Angular2中提供了依赖注入的概念,使得 ...
- 为什么做java的web开发我们会使用struts2,springMVC和spring这样的框架?
今年我一直在思考web开发里的前后端分离的问题,到了现在也颇有点心得了,随着这个问题的深入,再加以现在公司很多web项目的控制层的技术框架由struts2迁移到springMVC,我突然有了一个新的疑 ...
- Linux安装LAMP开发环境及配置文件管理
Linux主要分为两大系发行版,分别是RedHat和Debian,lamp环境的安装和配置也会有所不同,所以分别以CentOS 7.1和Ubuntu 14.04做为主机(L) Linux下安装软件,最 ...
- Concepts:Request 和 Task
当SQL Server Engine 接收到Session发出的Request时,SQL Server OS将Request和Task绑定,并为Task分配一个Workder.在TSQL Query执 ...
- spring源码分析之context
重点类: 1.ApplicationContext是核心接口,它为一个应用提供了环境配置.当应用在运行时ApplicationContext是只读的,但你可以在该接口的实现中来支持reload功能. ...
- Spring的数据库开发
Spring JDBC框架操作mysql数据库 Spring中的JDBC为我们省去连接和关闭数据库的代码,我们着重关注对数据库的操作.Sprin ...
- Performance Monitor4:监控SQL Server的IO性能
SQL Server的IO性能受到物理Disk的IO延迟和SQL Server内部执行的IO操作的影响.在监控Disk性能时,最主要的度量值(metric)是IO延迟,IO延迟是指从Applicati ...
- Ajax使用WCF实现小票pos机打印源码
通过ajax跨域方式调用WCF服务,实现小票pos机的打印,源码提供web方式,客户端方式测试,服务驻留右侧底部任务栏,可控制服务开启暂停,用户可自定义小票打印模板,配合零售录入. qq 22945 ...
- MSYS2环境下编译X265
HEVC(High Efficiency Video Coding),是一种新的视频压缩标准.可以替代H.264/ AVC编码,使得保持相同质量的情况下,体积减少40%左右.目前有多种实现版本,x26 ...
- Atitit.cto 与技术总监的区别
Atitit.cto 与技术总监的区别 1. 核心区别1 2. Cto主要职责1 3. 如何提升到cto1 4. CTO五种基本的必备素质:2 5. 2 1. 核心区别 技术总监(Chief Tech ...