飞翔飞翔
主页
  • 计算机基础

    • TCP/IP协议
    • Linux命令
  • 数据库

    • SQL教程
  • 编程语言

    • C语言
    • Python2
    • Python3
  • 数据格式

    • JSON教程
  • 工具

    • Markdown指南
  • Git

    • GitFlow
  • Quartz

    • Quartz教程
  • Java

    • Java设计模式
  • 缓存

    • Redis教程
联系
阿里云
主页
  • 计算机基础

    • TCP/IP协议
    • Linux命令
  • 数据库

    • SQL教程
  • 编程语言

    • C语言
    • Python2
    • Python3
  • 数据格式

    • JSON教程
  • 工具

    • Markdown指南
  • Git

    • GitFlow
  • Quartz

    • Quartz教程
  • Java

    • Java设计模式
  • 缓存

    • Redis教程
联系
阿里云
  • 学习路径
  • 第1章 认识Python

    • Python 历史与特点
    • Python 2 与 Python 3 的核心差异
    • 安装与运行 Python 2.7.18
    • 编码规范 PEP 8
  • 第2章 基础语法

    • 变量与对象
    • 数字类型
    • 字符串 str
    • Unicode 字符串
    • 运算符
    • 空值 None
  • 第3章 流程控制

    • if 条件语句
    • if-else 条件语句
    • if-elif-else 多分支
    • 条件表达式(三元运算符)
    • while 循环
    • for 循环
    • range 与 xrange
    • 循环控制:break、continue、pass
    • 循环 else 子句
  • 第4章 数据结构

    • 列表基础
    • 列表方法
    • 列表推导式
    • 元组
    • 字典基础
    • 字典方法
    • 字典循环技巧
    • 集合
    • 序列解包
    • 序列比较
  • 第5章 函数

    • 定义函数
    • 参数传递机制
    • 默认参数
    • 关键字参数
    • 可变参数
    • Lambda 表达式
    • 文档字符串
    • 函数对象
  • 第6章 模块与包

    • import 导入
    • 模块搜索路径
    • name 与主程序
    • 编译文件 .pyc 与 .pyo
    • 包结构
    • dir() 函数
  • 第7章 文件与IO

    • 打开与关闭文件
    • 文件读写方法
    • with 上下文管理器
    • 格式化输出:% 操作符
    • 格式化输出:str.format()
    • JSON 序列化
  • 第8章 面向对象

    • 类定义与实例化
    • init 构造方法
    • 类变量与实例变量
    • 方法调用与 self
    • 继承基础
    • 多重继承
    • 新式类与旧式类
    • 私有变量与名称改写
    • 属性装饰器 property
    • 类方法与静态方法
    • 魔术方法
    • 空类与数据记录
  • 第9章 异常处理

    • 异常类型
    • try-except
    • try-except-else-finally
    • 抛出异常 raise
    • 自定义异常
    • with 语句与上下文管理器
  • 第10章 迭代器与生成器

    • 迭代器协议
    • 生成器函数
    • 生成器表达式
    • itertools模块
  • 第11章 标准库精要

    • os模块
    • sys模块
    • datetime模块
    • re模块
    • json模块
    • collections模块
    • math与random模块
    • urllib2与网络请求
    • subprocess与命令执行
    • threading与并发
    • unittest与测试
    • 虚拟环境与包管理
  • 第12章 工程实践

    • 调试技巧
    • 性能分析
    • 文档与注释
    • 下一步学习

re模块

re 模块提供正则表达式支持,用于复杂的字符串匹配、查找、替换和分割。正则表达式是处理文本数据的强大工具,但语法复杂,需要逐步学习。

基本匹配

re.search:搜索第一个匹配

import re

match = re.search(r"\d+", "abc123def")
if match:
    print match.group()     # 123
    print match.start()     # 3
    print match.end()       # 6
    print match.span()      # (3, 6)

r"..." 是原始字符串,避免反斜杠转义问题。\d+ 匹配一个或多个数字。

re.match:从字符串开头匹配

print re.match(r"\d+", "abc123")       # None —— 开头不是数字
print re.match(r"\d+", "123abc")       # 匹配 "123"

match 等价于 search 加上 ^ 锚点。

re.findall:查找所有匹配

print re.findall(r"\d+", "abc123def456")     # ['123', '456']
print re.findall(r"[a-z]+", "abc123def456")   # ['abc', 'def']

re.finditer:返回迭代器(节省内存)

for match in re.finditer(r"\d+", "abc123def456"):
    print match.group(), match.span()
# 123 (3, 6)
# 456 (9, 12)

常用模式

模式含义示例
.任意字符(除换行)a.c 匹配 "abc"
\d数字\d{3} 匹配 3 位数字
\w单词字符(字母数字下划线)\w+ 匹配单词
\s空白字符\s+ 匹配空格
^字符串开头^Hello
$字符串结尾world$
*0 次或多次a*
+1 次或多次a+
?0 次或 1 次a?
{n}恰好 n 次a{3}
{n,m}n 到 m 次a{2,4}
[]字符集[abc] 匹配 a/b/c
|或cat|dog
()分组(\d+)-(\d+)

分组捕获

import re

# 提取日期各部分
text = "Date: 2024-01-15"
match = re.search(r"(\d{4})-(\d{2})-(\d{2})", text)
if match:
    print match.group(0)    # 2024-01-15(完整匹配)
    print match.group(1)    # 2024(第一组)
    print match.group(2)    # 01(第二组)
    print match.group(3)    # 15(第三组)
    print match.groups()    # ('2024', '01', '15')

命名分组(Python 2.7 支持):

match = re.search(r"(?P<year>\d{4})-(?P<month>\d{2})-(?P<day>\d{2})", text)
print match.group("year")       # 2024
print match.groupdict()         # {'year': '2024', 'month': '01', 'day': '15'}

替换

re.sub:替换匹配内容

text = "Hello 123 world 456"
result = re.sub(r"\d+", "NUM", text)
print result            # Hello NUM world NUM

# 使用函数动态替换
result = re.sub(r"\d+", lambda m: str(int(m.group()) * 2), text)
print result            # Hello 246 world 912

re.subn:替换并返回次数

result, count = re.subn(r"\d+", "NUM", text)
print result, count     # Hello NUM world NUM, 2

分割

re.split:按正则分割

text = "apple, banana; orange  lemon"
fruits = re.split(r"[,;\s]+", text)
print fruits            # ['apple', 'banana', 'orange', 'lemon']

比 str.split() 更灵活,支持多个分隔符。

编译正则

频繁使用的正则应该编译,提高性能:

pattern = re.compile(r"\d{4}-\d{2}-\d{2}")

# 多次使用
print pattern.search("Date: 2024-01-15")
print pattern.search("Date: 2024-02-20")
print pattern.findall("2024-01-15 and 2024-02-20")

编译后的正则对象有相同的方法:search、match、findall、sub 等。

标志位

import re

# 忽略大小写
re.search(r"hello", "HELLO", re.IGNORECASE)

# 多行模式(^$ 匹配每行开头结尾)
re.search(r"^start", "line1\nstart here", re.MULTILINE)

# 点号匹配换行
re.search(r"a.b", "a\nb", re.DOTALL)

# 组合标志
re.search(r"pattern", text, re.IGNORECASE | re.MULTILINE)

实际应用

验证邮箱:

def is_valid_email(email):
    pattern = r"^[\w\.-]+@[\w\.-]+\.\w+$"
    return re.match(pattern, email) is not None

print is_valid_email("user@example.com")    # True
print is_valid_email("invalid.email")       # False

提取 URL:

text = "Visit https://example.com or http://test.org"
urls = re.findall(r"https?://[^\s]+", text)
print urls              # ['https://example.com', 'http://test.org']

解析日志:

log_line = "192.168.1.1 - - [15/Jan/2024:14:30:25 +0800] \"GET /index.html HTTP/1.1\" 200 1234"

pattern = re.compile(
    r'^(\S+) \S+ \S+ \[(.+?)\] "(\S+) (\S+) \S+" (\d+) (\S+)'
)
match = pattern.match(log_line)
if match:
    ip, time, method, path, status, size = match.groups()
    print ip, method, path, status

清理文本:

def clean_text(text):
    # 去除多余空白
    text = re.sub(r"\s+", " ", text)
    # 去除特殊字符
    text = re.sub(r"[^\w\s]", "", text)
    return text.strip()

print clean_text("  Hello!!!   World...  ")     # Hello World

贪婪 vs 非贪婪

默认贪婪(匹配尽可能多的字符):

print re.search(r"<.*>", "<div>content</div>").group()
# <div>content</div> —— 贪婪,匹配到最后的 >

非贪婪(?)匹配尽可能少:

print re.search(r"<.*?>", "<div>content</div>").group()
# <div> —— 非贪婪,匹配到第一个 >

注意事项

  • 正则表达式可读性差,复杂模式建议加注释或拆分
  • 对于简单操作(固定字符串查找),str 方法更快:"abc" in text
  • 正则注入:不要直接用用户输入构造正则,可能引发 ReDoS(正则拒绝服务)
上一页
datetime模块
下一页
json模块