美文网首页Python学习
Python中re模块的介绍—正则表达式

Python中re模块的介绍—正则表达式

作者: 黄晶_id | 来源:发表于2019-12-07 16:36 被阅读0次

    黑马程序员Python45期讲义笔记

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

    正则表达式的概述

    1. 正则表达式的介绍

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

    2. 正则表达式概念

    正则表达式就是记录文本规则的代码

    3. 正则表达式实例

    0\d{2}-\d{8} 这个就是一个正则表达式,表达的意思是匹配的是座机号码

    4. 正则表达式的特点

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

    re模块的介绍

    首先要导入模块:import re
    match方法进行匹配操作用法:result = re.match(正则表达式,要匹配的字符串)
    如果上一步匹配到数据的话,可以使用group方法来提取数据:result.group()

    ### 导入re模块
    import re
    
    ### 使用match方法进行匹配操作
    result = re.match(正则表达式,要匹配的字符串)
    
    ### 如果上一步匹配到数据的话,可以使用group方法来提取数据
    result.group()
    

    rem模块的使用

    从字符串huangjing6344@novogene.com中匹配出huangjing

    import re
    
    # 使用match方法进行匹配操作
    result = re.match("huangjing","huangjing6344@novogene.com")
    # 获取匹配结果
    info = result.group()
    print(info)
    

    运行结果:

    huangjing
    

    再来,如果我想从字符串huangjing6344@novogene.com中匹配出novogene就会报错:

    import re
    
    # 使用match方法进行匹配操作
    result = re.match("novogene","huangjing6344@novogene.com")
    # 获取匹配结果
    info = result.group()
    print(info)
    

    报错结果:

    Traceback (most recent call last):
      File "C:/Users/huangjing00liang/Desktop/练习.py", line 6, in <module>
        info = result.group()
    AttributeError: 'NoneType' object has no attribute 'group'
    

    为什么呀?匹配出huangjingnovogene按说是一个道理呀?
    因为 re.match() 根据正则表达式从头开始匹配字符串数据

    错误分析:
    属性错误:'NoneType' 对象没有属性 'group'
    说明由re.match()函数返回给变量match的是一个空的类型,所以在调用group()方法时会报错。
    为什么会返回一个空变量呢?
    是因为这个函数是从一个字符串的开始位置匹配正则表达式,然而这个字符串的起始位置并不符合正则表达式,所以匹配失败,返回一个空变量,空变量并没有group()方法,所以调用不成功。

    匹配单个字符

    正则表达式的单字符匹配

    示例1:\d — 匹配一个数字,即0-9

    我想找到这句话Total number of C's analysed: 27474733里面的数字
    "\d+"匹配多个数字:

    import re
    
    ret = re.search(r"\d+","Total number of C's analysed:   27474733")
    print(ret.group())
    

    运行结果:

    27474733
    

    "\d"匹配一个数字:

    import re
    
    ret = re.search("\d","Total number of C's analysed: 27474733")
    print(ret.group())
    

    运行结果:

    2
    

    体会下"\d""\d+" 的区别

    示例2:. — 匹配任意1个字符(除了\n)

    注意:是一个哦

    import re
    
    ret = re.match(".","raw_data")
    print(ret.group())
    
    ret = re.match("raw.","raw_data")
    print(ret.group())
    
    ret = re.match("raw_.","raw_data")
    print(ret.group())
    

    运行结果:

    r
    raw_
    raw_d
    

    示例3:[] — 匹配[ ]中列举的1个字符

    如果hello的首字符小写,那么正则表达式需要小写的h:

    import re
    
    ret = re.match("h","hello Python")
    print(ret.group())
    

    运行结果:

    h
    

    如果hello的首字符大写,那么正则表达式需要大写的H:

    import re
    
    ret = re.match("H","Hello Python")
    print(ret.group())
    

    运行结果:

    H
    

    使用[]匹配大小写h都可以:

    import re
    
    ret = re.match("[hH]","hello Python")
    print(ret.group())
    ret = re.match("[hH]","Hello Python")
    print(ret.group())
    ret = re.match("[hH]ello Python","Hello Python")
    print(ret.group())
    

    运行结果:

    h
    H
    Hello Python
    

    匹配0到9另一种写法:

    import re
    
    ret = re.search("[0123456789]+","huangjing6344@novogene.com")
    print(ret.group())
    

    运行结果:

    6344
    

    匹配0到9另一种写法:

    import re
    
    ret = re.search("[0-9]","huangjing6344@novogene.com")
    print(ret.group())
    
    ret = re.search("[0-9]+","huangjing6344@novogene.com")
    print(ret.group())
    

    运行结果:

    6
    6344
    

    下面这个正则不能够匹配到数字4:

    import re
    
    ret = re.search("[0-35-9]+","huangjing6344@novogene.com")
    print(ret.group())
    

    运行结果:

    63
    

    示例4:\D — 表示匹配一个非数字,即不是数字

    注意"\D"和"\D+"的区别:

    import re
    
    match_obj = re.match("\D", "huangjing6344@novogene.com")
    print(match_obj.group())
    
    match_obj = re.match("\D+", "huangjing6344@novogene.com")
    print(match_obj.group())
    

    运行结果:

    h
    huangjing
    

    示例5:\s — 匹配一个空白字符,即空格和tab键

    空格属于空白字符:

    import re
    
    match_obj = re.match("hello\sworld", "hello world")
    if match_obj:
        result = match_obj.group()
        print(result)
    else:
        print("匹配失败")
    

    运行结果:

    hello world
    

    \t也属于空白字符:

    import re
    
    match_obj = re.match("hello\sworld", "hello world")
    if match_obj:
        result = match_obj.group()
        print(result)
    else:
        print("匹配失败")
    

    运行结果:

    hello world
    

    示例6:\S — 匹配一个非空白

    import re
    
    match_obj = re.search("\S", "hello&world")
    print(match_obj.group())
    
    match_obj = re.search("hello\Sworld", "hello&world")
    print(match_obj.group())
    

    运行结果:

    h
    hello&world
    

    示例7:\w — 匹配一个非特殊字符,即a-z、A-Z、0-9、_、汉字

    import re
    
    # 匹配非特殊字符中的一位
    match_obj = re.match("\w", "huangjing6344@novogene.com")
    print(match_obj.group())
    
    # 匹配非特殊字符中的多位
    match_obj = re.match("\w+", "huangjing6344@novogene.com")
    print(match_obj.group())
    

    运行结果:

    h
    huangjing6344
    

    示例8:\W — 匹配一个特殊字符,即非字母、非数字、非汉字

    import re
    
    match_obj = re.search("\W", "huangjing6344@novogene.com")
    print(match_obj.group())
    

    运行结果:

    @
    

    注意这里使用re.match会报错,因为huangjing6344@novogene.com中的特殊字符没在开头(如果是在开头那使用re.matchre.search是一样的效果):

    import re
    
    match_obj = re.match("\W", "huangjing6344@novogene.com")
    print(match_obj.group())
    

    报错:

    Traceback (most recent call last):
      File "C:/Users/huangjing00liang/Desktop/练习.py", line 5, in <module>
        print(match_obj.group())
    AttributeError: 'NoneType' object has no attribute 'group'
    

    总结:

    • . 表示匹配任意1个字符(除了\n)
    • [ ] 表示匹配[ ]中列举的1个字符
    • \d 表示匹配一个数字,即0-9
    • \D 表示匹配一个非数字,即不是数字
    • \s 表示匹配一个空白字符,即 空格,tab键
    • \S 匹配一个非空白字符
    • \S 匹配一个非空白字符
    • \W 匹配一个特殊字符,即非字母、非数字、非汉字

    匹配多个字符

    匹配多个字符

    示例1:* — 匹配前一个字符出现0次或者无限次,即可有可无

    匹配出一个字符串第一个字母为大写字符,后面都是小写字母并且这些小写字母可有可无:

    import re
    
    ret = re.match("[A-Z][a-z]*","Huangjing6344")
    print(ret.group())
    
    ret = re.match("[A-Z][a-z]*","HuangJing6344")
    print(ret.group())
    

    运行结果:

    Huangjing
    Huang
    

    匹配出一个字符串开头的大写字母:

    import re
    
    ret = re.match("[A-Z]*","Huangjing6344")
    print(ret.group())
    
    ret = re.match("[A-Z]*","HJing6344")
    print(ret.group())
    

    运行结果:

    H
    HJ
    

    示例2:+ — 匹配前一个字符出现1次或者无限次,即至少有1次

    匹配一个字符串,第一个字符是h,最后一个字符串是g,中间至少有一个字符:

    import re
    
    ret = re.match("h.+g","huangjing6344")
    print(ret.group())
    

    运行结果:

    huangjing
    

    示例3:? — 匹配前一个字符出现1次或者0次,即要么有1次,要么没有

    匹配出这样的数据,但是https 这个s可能有,也可能是http 这个s没有

    import re
    
    ret = re.match("https?", "http")
    print(ret.group())
    
    ret = re.match("https?", "https")
    print(ret.group())
    

    运行结果:

    http
    https
    

    示例4:{m}、{m,n}

    • {m}表示匹配前一个字符出现m次
    • {m,n}表示匹配前一个字符出现从m到n次
    import re
    
    ret = re.match("[a-zA-Z0-9_]{8}","huang00jing")
    print(ret.group())
    
    ret = re.match("[a-zA-Z0-9_]{5,8}","huang00jing")
    print(ret.group())
    

    运行结果:

    huang
    huang00j
    

    总结:

    • * 表示匹配前一个字符出现0次或者无限次,即可有可无
    • + 表示匹配前一个字符出现1次或者无限次,即至少有1次
    • ? 表示匹配前一个字符出现1次或者0次,即要么有1次,要么没有
    • {m} 表示匹配前一个字符出现m次
    • {m,n} 表示匹配前一个字符出现从m到n次

    匹配开头和结尾

    匹配开头和结尾

    示例1:^ — 匹配字符串开头

    需求:匹配以数字开头的数据

    import re
    
    # 匹配以数字开头的数据
    match_obj = re.match("^\d.*", "1.QC_Methy")
    if match_obj:
        # 获取匹配结果
        print(match_obj.group())
    else:
        print("匹配失败")
    

    运行结果:

    1.QC_Methy
    

    示例2:$ — 匹配字符串结尾

    需求: 匹配以数字结尾的数据

    import re
    # 匹配以数字结尾的数据
    match_obj = re.match(".*\d$", "huangjing6344")
    if match_obj:
        # 获取匹配结果
        print(match_obj.group())
    else:
        print("匹配失败")
    

    运行结果:

    huangjing6344
    

    示例3:^ 和 $

    需求: 匹配以数字开头中间内容不管以数字结尾

    import re
    match_obj = re.match("^\d.*\d$", "0.log_1")
    if match_obj:
        # 获取匹配结果
        print(match_obj.group())
    else:
        print("匹配失败")
    

    运行结果:

    0.log_1
    

    除了指定字符以外都匹配

    • [^指定字符]: 表示除了指定字符都匹配
    • 例如:[^h]: 表示除了指定字符h以外都匹配
    import re
    
    match_obj = re.match("[^h]", "jing")
    if match_obj:
        # 获取匹配结果
        print(match_obj.group())
    else:
        print("匹配失败")
    

    运行结果:

    j
    

    总结:

    • ^ 表示匹配字符串开头
    • $ 表示匹配字符串结尾

    匹配分组

    匹配分组相关正则表达式

    示例1:| — 匹配左右任意一个表达式

    需求:在列表中["apple", "banana", "orange", "pear"],匹配apple和pear

    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)
    

    运行结果:

    apple是我想要的
    banana不是我要的
    orange不是我要的
    pear是我想要的
    

    示例2:( ) — 将括号中字符作为一个分组

    需求:匹配出163、126、qq等邮箱

    import re
    
    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(1))
    else:
        print("匹配失败")
    

    运行结果:

    hello@163.com
    163
    

    需求: 匹配qq:10567这样的数据,提取出来qq文字和qq号码

    import re
    
    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("匹配失败")
    

    运行结果:

    qq:10567
    qq
    10567
    

    示例3:\num — 引用分组num匹配到的字符串

    需求:匹配出<html>hh</html>

    import re
    
    match_obj = re.match("<[a-zA-Z1-6]+>.*</[a-zA-Z1-6]+>", "<html>hh</div>")
    
    if match_obj:
        print(match_obj.group())
    else:
        print("匹配失败")
    
    ###引用分组1匹配到的字符串
    ### 正则表达式中必须是两个斜杠:\\1
    match_obj = re.match("<([a-zA-Z1-6]+)>.*</\\1>", "<html>hh</html>")
    
    if match_obj:
        print(match_obj.group())
    else:
        print("匹配失败")
    

    示例4:(?P<name>) (?P=name) — 引用别名为name分组匹配到的字符串

    匹配出<html><h1>www.processon.com</h1></html>:

    import re
    match_obj = re.match("<(?P<name1>[a-zA-Z1-6]+)><(?P<name2>[a-zA-Z1-6]+)>.*</(?P=name2)></(?P=name1)>", "<html><h1>www.processon.com</h1></html>")
    
    if match_obj:
        print(match_obj.group())
    else:
        print("匹配失败")
    

    运行结果:

    <html><h1>www.processon.com</h1></html>
    

    注意:

    • 分组的数据是从左向右的方式进行分配的
    • re.match 只匹配字符串的开始,如果字符串开始不符合正则表达式,则匹配失败,函数返回None;而re.search匹配整个字符串,直到找到一个匹配。

    总结:

    • | 表示匹配左右任意一个表达式
    • (ab) 表示将括号中字符作为一个分组
    • \num 表示引用分组num匹配到的字符串
    • (?P<name>) 表示分组起别名
    • (?P=name) 表示引用别名为name分组匹配到的字符串
    • (分组数据) 分组数是从左到右的方式进行分配的,最左边的是第一个分组,依次类推

    相关文章

      网友评论

        本文标题:Python中re模块的介绍—正则表达式

        本文链接:https://www.haomeiwen.com/subject/qjfjgctx.html