文章目录
- 介绍
- 基本语法
- 常用函数
- 捕获组和命名组
- 非捕获组
- 贪婪匹配和非贪婪匹配
- 多行模式和点匹配所有模式
- 示例总结
介绍
Python 中的正则表达式(regular expressions, 简称 regex)由 re
模块提供。正则表达式是一种用于匹配字符串的强大工具,常用于文本搜索和处理。以下是一些常用的正则表达式语法及其相关说明:
基本语法
-
普通字符: 直接匹配字符本身。
- 示例:
abc
匹配字符串 “abc”。
- 示例:
-
点号 (
.
): 匹配除换行符以外的任意字符。- 示例:
a.c
匹配 “abc”、“a1c” 等。
- 示例:
-
字符集 (
[]
): 匹配方括号中的任意一个字符。- 示例:
[abc]
匹配 “a”、“b” 或 “c”。
- 示例:
-
字符范围: 在字符集内使用
-
表示范围。- 示例:
[a-z]
匹配所有小写字母。
- 示例:
-
排除字符集 (
[^]
): 匹配不在方括号内的任意字符。- 示例:
[^abc]
匹配除 “a”、“b”、“c” 之外的任意字符。
- 示例:
-
重复次数:
-
*
: 匹配前面的字符0次或多次。
- 示例:
a*
匹配空字符串、“a”、“aa” 等。
- 示例:
-
+
: 匹配前面的字符1次或多次。
- 示例:
a+
匹配 “a”、“aa” 等。
- 示例:
-
?
: 匹配前面的字符0次或1次。
- 示例:
a?
匹配空字符串或 “a”。
- 示例:
-
{m,n}
: 匹配前面的字符至少
m
次,至多
n
次。
- 示例:
a{2,4}
匹配 “aa”、“aaa” 或 “aaaa”。
- 示例:
-
-
边界匹配:
-
^
: 匹配字符串的开头。
- 示例:
^abc
匹配以 “abc” 开头的字符串。
- 示例:
-
$
: 匹配字符串的结尾。
- 示例:
abc$
匹配以 “abc” 结尾的字符串。
- 示例:
-
\b
: 匹配单词边界。
- 示例:
\bword\b
匹配独立的单词 “word”。
- 示例:
-
-
特殊字符:
\d
: 匹配任意数字,等价于[0-9]
。\D
: 匹配任意非数字字符,等价于[^0-9]
。\w
: 匹配任意字母数字字符,等价于[a-zA-Z0-9_]
。\W
: 匹配任意非字母数字字符,等价于[^a-zA-Z0-9_]
。\s
: 匹配任意空白字符,包括空格、制表符、换行符等。\S
: 匹配任意非空白字符。
常用函数
-
re.match(pattern, string)
: 从字符串的开头尝试匹配模式。-
示例:
python
Copy code
import re result = re.match(r'\d+', '123abc') if result:print(result.group()) # 输出: 123
-
-
re.search(pattern, string)
: 搜索整个字符串,返回第一个匹配的结果。-
示例:
python
Copy code
result = re.search(r'\d+', 'abc123def') if result:print(result.group()) # 输出: 123
-
-
re.findall(pattern, string)
: 搜索整个字符串,返回所有匹配的结果列表。-
示例:
python
Copy code
results = re.findall(r'\d+', 'abc123def456') print(results) # 输出: ['123', '456']
-
-
re.sub(pattern, repl, string)
: 替换字符串中所有匹配的子串。-
示例:
python
Copy code
result = re.sub(r'\d+', '#', 'abc123def456') print(result) # 输出: abc#def#
-
-
re.split(pattern, string)
: 根据模式分割字符串,返回一个列表。-
示例:
python
Copy code
import re result = re.split(r'\d+', 'abc123def456ghi') print(result) # 输出: ['abc', 'def', 'ghi']
-
-
re.compile(pattern)
: 编译正则表达式模式,返回一个正则表达式对象,后续可以使用该对象调用匹配方法。-
示例:
python
Copy code
pattern = re.compile(r'\d+') result = pattern.match('123abc') if result:print(result.group()) # 输出: 123
-
捕获组和命名组
-
捕获组: 使用圆括号
()
将部分模式括起来,匹配的子串会被捕获到一个组中。-
示例:
python
Copy code
match = re.search(r'(\d+)-(\d+)', '123-456') if match:print(match.group(1)) # 输出: 123print(match.group(2)) # 输出: 456
-
-
命名组: 使用
(?P<name>...)
语法给捕获组命名,便于后续引用。-
示例:
python
Copy code
match = re.search(r'(?P<area_code>\d+)-(?P<number>\d+)', '123-456') if match:print(match.group('area_code')) # 输出: 123print(match.group('number')) # 输出: 456
-
非捕获组
有时你可能只想对一部分模式进行分组,但不希望捕获匹配结果。此时可以使用非捕获组 (?:...)
。
-
示例:
python
Copy code
match = re.search(r'(?:\d+)-(\d+)', '123-456') if match:print(match.group(1)) # 输出: 456
贪婪匹配和非贪婪匹配
-
贪婪匹配: 默认情况下,量词 (
*
,+
,{m,n}
) 是贪婪的,会尽可能多地匹配字符。-
示例:
python
Copy code
match = re.search(r'<.*>', '<tag>content</tag>') if match:print(match.group()) # 输出: <tag>content</tag>
-
-
非贪婪匹配: 在量词后面加
?
可以使其变为非贪婪匹配,尽可能少地匹配字符。-
示例:
python
Copy code
match = re.search(r'<.*?>', '<tag>content</tag>') if match:print(match.group()) # 输出: <tag>
-
多行模式和点匹配所有模式
-
多行模式 (
re.MULTILINE
): 使^
和$
匹配每一行的开头和结尾,而不仅仅是整个字符串的开头和结尾。-
示例:
python
Copy code
text = """first line second line""" matches = re.findall(r'^\w+', text, re.MULTILINE) print(matches) # 输出: ['first', 'second']
-
-
点匹配所有模式 (
re.DOTALL
): 使.
匹配所有字符,包括换行符。-
示例:
python
Copy code
text = "line one\nline two" match = re.search(r'line.*', text, re.DOTALL) if match:print(match.group()) # 输出: line one\nline two
-
示例总结
综合应用上述语法和函数,下面是一个更复杂的示例:
python
Copy code
import retext = """
John Doe, email: john.doe@example.com, phone: (123) 456-7890
Jane Smith, email: jane.smith@example.com, phone: (987) 654-3210
"""# 提取所有的 email 地址
emails = re.findall(r'\b[\w.-]+?@\w+?\.\w+?\b', text)
print("Emails:", emails)# 提取所有的电话号码
phones = re.findall(r'\(\d{3}\) \d{3}-\d{4}', text)
print("Phones:", phones)# 提取姓名