文章目录

  • 正则表达式与re模块
  • 字符匹配
    • 普通字符匹配
    • 利用元字符进行模糊匹配
      • 元字符: . ^ $ + ? {} [] | () \
      • 重复的字符匹配
  • re模块下的其他方法

今天总结一下正则表达式,它用来解决模糊匹配的问题,几乎在所有编程语言中都可以用,尤其在python爬虫中,它是一门必修知识;
所谓模糊匹配,就是在匹配字符串中,有一部分是确定的,另一部分是不确定的值但有范围的任意值;
这样我们就可以用一些具有特殊含义的符号,对字符串进行另一种描述,而这些特殊含义的符号就组成一个正则表达式。

正则表达式与re模块

正则表达式也内嵌在Python中,通过re模块来实现,常用方法是findall(),会将匹配到的字符串用一个列表返回
例如: 要匹配一大串字符串中的所有数字,不用for循环和If语句,用re模块一行就能实现

import re
print(re.findall('\d+',"sadfjk11ksk22iuir33bndb44uidu55sgsfir66o77"))

运行结果:

字符匹配

普通字符匹配

import re
print(re.findall('bigbig',"Iwannaabigbigjuicecanyougiveme?"))
#findall第一个参数是需要匹配的子串或子串规则,第二个参数为母串

运行结果:

利用元字符进行模糊匹配

元字符: . ^ $ + ? {} [] | () \
  1. .任意字符:
import re
#匹配b开头g结尾的子串,..表示任意的两个字符,如果不是两个,那就匹配不出来
print(re.findall('b..g',"abcdefgabcdghijklmn"))

运行结果:

  1. ^只能为开头:
import re
#匹配b开头g结尾的子串
#^表示子串的第一个字符只能在母串的开头,..表示任意的两个字符
print(re.findall('^b..g',"bbcgefgabcdghijblmg"))

运行结果:

  1. $只能以结尾:
import re
#匹配b开头g结尾的子串
#$表示子串的最后一个字符只能在母串的结尾,..表示任意的两个字符
print(re.findall('b..g$',"abcdefgabcdghijblmg"))

运行结果:

重复的字符匹配
  1. 贪婪匹配: 即尽量多地匹配,与之相反的是惰性匹配

  2. *是0到无穷个:

import re
#*表示子串的某个字符可以0到无穷次出现
print(re.findall('Wo23*Le',"sjfkufiWo233333333333333333333Le"))

运行结果:

  1. +是1到无穷个:
import re
#+表示子串的某个字符可以1到无穷次出现(该元素至少出现一次),..表示任意的两个字符
print(re.findall('Wo23+Le',"sjfkufiWo233333333333333333333Le"))
#与*的区别匹配
print(re.findall('Wo23*',"dsjfkjfiWo2"))  #能匹配到内容
print(re.findall('Wo23+',"dsjfkjfiWo2"))  #不能匹配到内容,因为3要至少要出现一次

运行结果:

  1. ?匹配0次到1次:
import re
#匹配b开头g结尾的子串
#?表示子串的某个字符可以出现0到1次
print(re.findall('beii?',"abcdefghibeigggjklmn"))  #母串bei后面是g,不是i,所以不匹配bei后的i
print(re.findall('beig?',"abcdefghibeigggjklmn"))  #母串bei后有g,就匹配1次g

运行结果:

  1. {}任意规定次数:
import re
#{a,b}表示子串的某个字符可以出现a到b次,同时可表现*,+,?
#{0,}==*    {1,}==+     {0,1}==?
#匹配b开头g结尾的子串
print(re.findall('beig{6}',"abcdefghibeiggggggjklmn"))
#{n}没有规定范围,而只有一个参数时,表示严格执行重复n次,多了和少了都匹配不出来

运行结果:

  1. 在后加?变成惰性匹配
    以上四个都是贪婪匹配, + ? {}后面加一个?就可以变成惰性*匹配(尽可能少地匹配)
import re
print(re.findall('Wo23*',"sjfkufiWo233333333333333333333"))
print(re.findall('Wo23+',"sjfkufiWo233333333333333333333"))
print(re.findall('beig?',"abcdefghibeigggjklmn"))#加?变惰性匹配,最终子串中的某个字都尽量少地匹配,匹配0次即不算进子串里面
print(re.findall('Wo23*?',"sjfkufiWo233333333333333333333"))  #匹配0次
print(re.findall('Wo23+?',"sjfkufiWo233333333333333333333"))  #匹配1次
print(re.findall('beig??',"abcdefghibeigggjklmn"))  #匹配0次#但这样匹配加?后就没有效果了,因为末尾还有需要匹配的字符,所以不会变成懒惰
print(re.findall('Wo23*?Le',"sjfkufiWo233333333333333333333Le"))
print(re.findall('Wo23+?Le',"sjfkufiWo233333333333333333333Le"))

运行结果:

  1. []选择匹配:
import re
#[]表示选择[]中的一个字符进行匹配,可以当做‘或’来理解,只要母串有就可以匹配出来
print(re.findall('x[yz]',"iiooxyjiushixzxxoo"))  #匹配出xy或xz
print(re.findall('x[yz]p',"iiooxypjiushixzpxxoo"))  #匹配出xyp或xzp#[]内的*,+等元字符都当做普通字符来匹配
print(re.findall('q[a*+?]',"iioojq*iusq+hiqaxxoo"))#但是有3个特殊符号(-范围  ^非  \跟元字符去除特殊功能,\跟普通字符实现特殊功能),如匹配字符串中的字母
print(re.findall('q[a-z]','234988436qfsabcdefg386'))  #a-z表示a到z任意字母,但是[]内终究只会匹配一个字符
print(re.findall('q[a-z]*','234988436qfabcdefg386'))  #[a-z]*表示任意字母重复任意次,因为贪婪,所以会把后面的字母全部匹配进去
print(re.findall('q[0-9]*','ddsljq5201314skdjfinfkd'))  #匹配任意数字
print(re.findall('q[^0-9]',"jkddafkjq123jiuqb"))  #匹配非数字

运行结果:

  1. \转义字符:
    \跟元字符去除特殊功能,\跟普通字符实现特殊功能
import re
#\d匹配数字字符,\D匹配非数字字符
print(re.findall('q\d',"jkddafkjq123jiuqb"))  #匹配一个数字字符
print(re.findall('\d',"jkjk1jkj3kji1hgh4o52knngygy0pp"))  #匹配所有数字字符,包括不连续的不连接#\s匹配任何空白字符(\t\n\r\f\v),\S匹配任何非空吧字符
print(re.findall('\S',"you are my girl"))#\w匹配_、字母、数字字符,\W匹配非_、字母、数字字符
print(re.findall('\w',"s&u#n——_shine"))#\\b匹配一个特殊字符边界,你需要的字符旁边有特殊字符
print(re.findall('I\\b',"may @I# am I from CHINA"))
#一个@I#中的I,一个单独的I和CHINA中的I,CHINA中的I周围没有特殊字符,所以不会匹配出来
print(re.findall(r'I\b',"may @I# am I from CHINA"))  #r和\b结合也有同样的效果
#其中r的意思是不让python做翻译,\b在python中和在正则中的意思不同,不翻译python这一层,
#就可以达到正则的效果。第一次执行的\\b也是利用\将\b变成在python中无意义,但在正则中有效

运行结果:

  1. |或,()分组:
import re
#|左右两边都匹配
print(re.findall('qa|you',"jiushiqa|youiushi"))
#()将字符分组(特殊格式)
print(re.findall('(?P<name>[A-z]+)(?P<age>\d+)',"LuFei19Suolong22"))  #匹配一串字母+一串数字#用search()来匹配,只会匹配遇到的第一个组
print(re.search('(?P<name>[A-z]+)(?P<age>\d+)',"LuFei19Suolong22"))
#用group()将分组好的元素取出来
print(re.search('(?P<name>[A-z]+)(?P<age>\d+)',"LuFei19Suolong22").group('age'))#match方法与search几乎相同,也是只会匹配遇到的第一个子串
print(re.match('\d+',"1314520jiushi2333333"))
print(re.match('\d+',"1314520jiushi2333333").group())

运行结果:

re模块下的其他方法

re模块下的方法,除了findall(),search()、match()还有以下几个常用的

  1. split()方法:分割字符串
import re
print(re.split('[ |]',"hello python|ok?"))  #将母串用空格和|分开
print(re.split('[mv]',"mtakemvab"))
#先匹配到m,将m前的空字符和后面的一串分开,得到''和'takemvab'
#又匹配到m,将m前的take分开,得到'take'和'vab'
#又匹配到v,将v前的''分开,得到''和'ab'

运行结果:

  1. sub()方法、subn()方法:替换字符串内容
import re
print(re.sub('\d+','Q',"take123away4567it"))  #将所有连续的数字替换成一个Q
print(re.sub('\d','Q',"take123away4567it"))  #将所有数字替换成Q
print(re.sub('\d','Q',"take123away4567it",4))  #将前四个数字替换成Q
print(re.subn('\d','Q',"take123away4567it"))  #替换后会返回替换的个数

运行结果:

  1. compile():自定义匹配规则
import re
dig = re.compile('\d+')  #设计一个匹配连续数字的规则,并将规则命名为dig
print(dig.findall("love18874her15157"))  #匹配时就可直接调用规则

运行结果:

  1. finditer():匹配后转换成迭代器
import re
ret = re.finditer('\d+',"love18874her15157Ok88")  #匹配结果是一个迭代器组成的组
print(next(ret).group())  #用next来遍历,用分组取出
print(next(ret).group())
print(next(ret).group())

运行结果:

  1. ()内的?:表示去优先级:
import re
print(re.findall('www\.(?:baidu|sina)\.com',"www.sina.com"))  #()分组会默认将分组拿出
print(re.findall('(abc)+',"xyzabcabcabcxyzxy"))  #()内默认只会匹配一个组的内容
print(re.findall('(?:abc)+',"xyzabcabcabcxyzxy"))  #其中?:去除优先级,则会匹配多个组的内容
print(re.findall('(abc)',"xyzabcabcabcxyzxy"))  #但可以匹配多个组(有严格分组),不管是否有优先级
print(re.findall('(?:abc)',"xyzabcabcabcxyzxy"))

运行结果:

到此为止,本篇文章已经总结完了正则表达式与Pythonre模块中的大部分用法。很多细节部分也都有所举例,所以内容比较多,希望读者能慢慢消化。或许你会觉得正则表达式有些太繁琐,但是,当你学到爬虫阶段的时候,就知道正则表达式是多么好用。而且,作为一个程序员,会正则是一项基本技能

初学者python笔记(re模块、正则表达式完全解析)相关推荐

  1. 初学者python笔记(模块篇)

    现在Python这门编程语言是越来越火了,其中的一个主要原因就是Python中有各种各样的模块,这是其他很多编程语言中都没有的.Python中这些模块都各有其功能,需要的时候直接导入就可以,简直不要太 ...

  2. 初学者python笔记(类的继承与多态---详解)

    文章目录 一.类的组合与继承的区别 二.类的继承 1.继承的功能分析 2.类的继承之派生.接口继承 3.用接口模块abc来实现接口继承 4.使用接口继承的好处 5.类的继承顺序 6.在子类中调用父类的 ...

  3. 初学者python笔记(map()函数、reduce()函数、filter()函数、匿名函数)

    文章目录 一.匿名函数 二.map()函数 三.reduce()函数 四.filter()函数 五.三大函数总结 本篇文章内容有Python中的匿名函数和map()函数.reduce()函数.filt ...

  4. 初学者python笔记(列表的食用方法)

    本篇是关于可迭代对象中的列表一些相关使用方法的记录. 可迭代对象简单描述:可以被for循环执行的对象(字符串,列表,元组,字典-) input()方法接收的其实只是字符串 a = input(&quo ...

  5. Python之re模块 —— 正则表达式操作

    Python之re模块 -- 正则表达式操作 转自:http://www.cnblogs.com/PythonHome/archive/2011/11/19/2255459.html 这个模块提供了与 ...

  6. 初学者python笔记(静态属性、类方法、静态方法、类的组合)

    文章目录 类的三大方法 1.静态属性 2.类方法.静态方法 3.三大方法总结 类的组合 1.用法分析 2.面试案例分析 本篇文章是上一篇:初学者python笔记(面向对象编程.类与对象)的后续篇,是关 ...

  7. 初学者python笔记(装饰器后篇:登陆验证)

    装饰器有非常强大的功能,可以不修改函数源代码和调用方式,就给函数加上了对应想要的功能,简直就是 修饰函数的利器. 上一篇文章:初学者python笔记(装饰器.高阶函数.闭包)已经非常详细的剖析了装饰器 ...

  8. 初学者python笔记(装饰器、高阶函数、闭包)

    一个函数被定义完成后,甚至程序发布后,后期可能需要添加某些功能,但是我们不可能每次都去修改原函数的代码,这时候装饰器就可以上场了,本篇文章将会用一个个可实现的代码,由浅入深.循序渐进得阐述装饰器的强大 ...

  9. 初学者python笔记(内置函数_2)

    这篇初学者笔记是接着上一篇初学者python笔记(内置函数_1)的.同样都是介绍Python中那些常用内置函数的. max()和min()的高级用法 我们都知道,max():取最大值,min():取最 ...

最新文章

  1. 快讯 | 清华成立AI研究院,与谷歌深度合作,张钹、姚期智、Jeff Dean坐镇
  2. c#属性的相关学习总结。
  3. linux查看CPU信息
  4. java编程中的断言工具类(org.springframework.util.Assert)
  5. 添加功能与测试点总结
  6. 移植RTT使用cubeMx配置后出现 cannot open source input file stm32f1xx_hal_exti.h: No such file or directory
  7. Python实现从url中提取域名的几种方法
  8. php多条件检索怎么写,sql查询同时满足三个条件 php查询数据库,同时满足三个条件的sql怎么写?...
  9. 自定义EasyUI图标样式
  10. html 怎么看版本号,怎样查看jquery版本号?
  11. 支持向量回归(Support Vector Regression)
  12. CC2420芯片手册核心知识点
  13. 第三章 MapReduce框架原理
  14. 离散数学:用python实现矩阵乘法与关系矩阵
  15. 走进小作坊(二十)----商道:胡雪岩叱咤商场的经营智慧
  16. c语言数组模拟骰子6000次,单选:模拟骰子的6000次投掷,编程统计并输出骰子的6个面各自出现的概率。按要求在空白处填写适当的表达式或语句,使程序完整并符合题目要求。...
  17. 如何判断网站SSL证书是否安装成功?
  18. 【hive】beeline常用操作指令
  19. 设置Office 365移动设备管理MDM服务——创建APNs证书
  20. 清华出品:最易懂的AI芯片报告!人才技术趋势都在这里

热门文章

  1. python如何确定拐点_如何确认均线拐点的实战技巧和理论(图解)
  2. python可视化工具bokeh_浅谈python可视化包Bokeh
  3. lq分解的matlab语言,MATLAB-语言及其应用.ppt
  4. vscode markdown_VS Code中的Markdown插件
  5. java能写驱动吗_使用纯java jdbc驱动程序实现数据库的连接
  6. python random模块导入_Python学习笔记(二十)—模块的导入
  7. DataGuard ORA-01111,ORA-01275文件创建失败问题解决
  8. 计算机中丢失api-ms-win-crt-locale,API-MS-WIN一系列丢失DLL打包
  9. linux不识别xfs,51CTO博客-专业IT技术博客创作平台-技术成就梦想
  10. 上传图片至服务器,写入到数据库Blob字段中,以及从数据库读取Blob信息(iframe父子页面传值)(1)