正则表达式学习(基础)
视频:【10分钟快速掌握正则表达式】 https://www.bilibili.com/video/BV1da4y1p7iZ/?share_source=copy_web&vd_source=2ab881ed926b454dc65f738c73aa19bd
正则表达式核心语法精讲
正则表达式就像一套“寻宝图”,它用特殊的符号告诉你“宝藏”(文本)长什么样,以及在哪里。
1. 限定符 (Quantifier) - “它要出现几次?”
限定符用来规定它前面的一个字符(或一组字符) 要出现多少次。
符号 | 含义与白话解释 | 举例 | 匹配例子 | 不匹配例子 |
---|---|---|---|---|
a* | a 出现 0 次或多次(可有可无,可以有多个) | ab*c | “ac”, “abc”, “abbc” | “a-c” |
a+ | a 至少出现 1 次或多次(必须有,可以有多个) | ab+c | “abc”, “abbc” | “ac” |
a? | a 出现 0 次或 1 次(要么没有,要么只有一个) | colou?r | “color”, “colour” | “colouur” |
a{6} | a 必须连续出现正好 6 次 | \d{4} | “1234”, “2020” | “123” |
a{2,6} | a 连续出现 2 到 6 次(不能多也不能少) | \d{2,4} | “12”, “123”, “1234” | “1”, “12345” |
a{2,} | a 至少连续出现 2 次(2次及以上) | a{2,} | “aa”, “aaa”, “aaaa” | “a” |
核心要点:限定符是修饰它左边最近的那个单元的。
2. 元字符 (Meta-characters) - “它是什么类型的字符?”
元字符是预先定义好的一些字符集合,用反斜杠 \
加一个字母表示,非常常用。
符号 | 含义与白话解释 | 举例 | 匹配例子 |
---|---|---|---|
\d | 匹配一个数字。等价于 [0-9] | \d\d | “12”, “00” |
\D | 匹配一个非数字字符。是 \d 的取反 | \D\D | “ab”, “@#” |
\w | 匹配一个单词字符(字母、数字、下划线) | \w\w\w | “A_b”, “a1c”, “中文” (视环境) |
\W | 匹配一个非单词字符(如@、#、空格、换行符)。是 \w 的取反 | \W | “@”, “ ” |
\s | 匹配一个空白字符(包括空格、制表符 Tab 、换行符) | a\sb | “a b” (中间有一个空格) |
\S | 匹配一个非空白字符。是 \s 的取反 | \S\S | “ab”, “1@” |
. | 通配符,匹配任意一个字符(除了换行符 \n ) | a.c | “abc”, “a@c”, “a c” |
\b | 边界符,不匹配任何字符,只匹配单词的边界(开头或结尾) | \bcat\b | 匹配 “a cat” 中的 “cat”,但不匹配 “category” 中的 “cat” |
^ | 开始符,匹配字符串的开头 | ^Hello | 匹配以 “Hello” 开头的字符串 |
$ | 结束符,匹配字符串的结尾 | world!$ | 匹配以 “world!” 结尾的字符串 |
核心要点:
\b
非常有用,用于“全字匹配”,比如在代码里把var
替换成let
,但又不想把variable
也替换了,就用\bvar\b
。^
和$
常用于验证。比如验证一个字符串是不是一个完整的手机号:^\d{11}$
(从开头到结尾必须是11位数字)。
3. 或运算符 (OR Operator) - “多个条件,满足一个就行”
符号 | 含义与白话解释 | 举例 | 匹配例子 |
---|---|---|---|
`(a | b)` | 匹配 a 或者 b | `(gray |
`(ab | cd)` | 匹配 ab 或者 cd | `(ab |
核心要点:括号 ()
不仅用于分组,还改变了优先级。gr(a|e)y
比 gray|grey
写起来更简洁。
4. 字符类 (Character Classes) - “在这个范围里挑一个”
字符类用方括号 []
表示,匹配括号内列出的任意一个字符。
符号 | 含义与白话解释 | 举例 | 匹配例子 |
---|---|---|---|
[abc] | 匹配 a 或者 b 或者 c 中的任意一个 | [aeiou] | 匹配任意一个元音字母 |
[a-c] | 同上,用了连字符 - 表示范围,更简洁 | [0-9] (等价于 \d ) | 匹配一个数字 |
[a-fA-F0-9] | 范围可以组合,匹配 a到f 或 A到F 或 0到9(即16进制数字) | [a-z] | 匹配任意一个小写字母 |
[^0-9] | ^ 在方括号内表示“非”,匹配不在0-9之间的任意一个字符(等价于 \D ) | [^aeiou] | 匹配任意一个非元音字母 |
核心要点:方括号 []
里的元字符(如 .
, *
)大部分会失去特殊含义,只代表字符本身。^
只有在方括号内第一个位置时才表示“非”。
5. 贪婪/懒惰匹配 (Greedy / Lazy Match) - “要多的还是要少的?”
这是正则中一个非常重要的高级概念。
- 贪婪匹配 (Greedy):默认模式。会匹配尽可能长的字符串。
- 懒惰匹配 (Lazy):在限定符后面加上一个问号
?
。会匹配尽可能短的字符串。
例子:对于字符串 H<em>Hello</em> <em>World</em>
正则表达式 | 模式 | 匹配结果(白话解释) |
---|---|---|
<.*> | 贪婪 | 整个 <em>Hello</em> <em>World</em> (它一口气吞下了从第一个 < 到最后一个 > 之间的所有内容) |
<.*?> | 懒惰 | 两次分别匹配 <em> 和 </em> (它一看到 > 就停止匹配,非常“懒”) |
核心要点:当你发现用 .*
匹配得到的内容太多,远超预期时,就应该考虑使用懒惰模式 .*?
。
总结与实践建议
这张图几乎涵盖了正则表达式最核心、最常用的语法。
- 学习顺序:先理解元字符(是什么),再掌握限定符(有多少),然后用或运算符和字符类构建更复杂的关系,最后在需要精确控制时使用懒惰匹配。
- 如何练习:一定要动手! 打开 regex101.com 或 regexr.com,把例子输进去,自己修改、测试,观察结果。这是最快的学习方法。
- 常见用途:
- 验证字符串:
^\d{11}$
(11位数字) - 提取信息:
(\d{4})-(\d{2})-(\d{2})
(从日志中提取年月日) - 替换文本:将
\bMr\b
替换为Mr.
(确保Mr后面有点)
- 验证字符串:
补充(GPT版):
可以把正则表达式想象成一种 “超级搜索和匹配工具” 或者 “文本的模版”。
它的核心只有一句话:用一种特殊的规则字符串,来定义你想要的文本模式,然后从一大段文字中快速找到、提取或替换所有符合这个模式的部分。
一、一个生动的比喻
想象一下,你在玩一个“找形状”的游戏:
- 规则: “找出所有以字母 ‘a’ 开头,以字母 ‘e’ 结尾的单词。”
- 文本: “apple, banana, orange, grape, axe”
- 结果: 你会找出 apple 和 axe。
这里的规则 “以a开头,以e结尾”
就是一个非常简单的“正则表达式”思想。而真正的正则表达式就是用一系列特殊符号,把这种自然语言描述的规则给“写”出来。
二、为什么需要它?(应用场景)
正则表达式非常强大,无处不在:
- 表单验证:检查用户输入的邮箱、手机号、密码强度是否符合格式。
- 数据提取:从网页源码、日志文件里快速抓出特定信息(如电话号码、日期、IP地址)。
- 文本替换:在代码编辑器或Word里,用一条规则批量替换所有重复的词语或错误的格式。
- 高级搜索:在大量文件中,搜索符合复杂条件的文本,而不是简单的某个词。
三、基础语法入门(从小白到入门)
我们先认识几个最常见的“特殊符号”,它们就是正则表达式的“字母”。
1. 匹配单个字符
符号 | 含义 | 举例 | 匹配内容 |
---|---|---|---|
. | 匹配任意一个字符(除了换行符) | a.c | “abc”, “aac”, “a@c” |
\d | 匹配一个数字 (0-9) | \d\d | “12”, “00”, “45” |
\w | 匹配一个字母、数字或下划线 | \w\w\w | “A_b”, “a1c”, “中文” |
\s | 匹配一个空白字符(空格、制表符等) | a\sb | “a b” |
[ ] | 匹配括号内的任意一个字符 | [aeiou] | 匹配任意一个元音字母 |
[0-9] (等价于 \d ) | 匹配一个数字 | ||
[a-zA-Z] | 匹配任意一个字母 |
2. 匹配多个字符(控制数量)
只匹配一个字符太少了,我们需要控制它出现的次数。
符号 | 含义 | 举例 | 匹配内容 | 不匹配内容 |
---|---|---|---|---|
* | 匹配前面的字符0次或多次 | ab*c | “ac”, “abc”, “abbc” | “a-c” |
+ | 匹配前面的字符1次或多次 | ab+c | “abc”, “abbc” | “ac” |
? | 匹配前面的字符0次或1次 | colou?r | “color”, “colour” | “colouur” |
{n} | 匹配前面的字符恰好n次 | \d{4} | “1234”, “2020” (4位数字) | “123” |
{n, m} | 匹配前面的字符n到m次 | \d{2,4} | “12”, “123”, “1234” | “1” |
3. 匹配位置
符号 | 含义 | 举例 | 匹配内容(仅匹配位置,不是字符) |
---|---|---|---|
^ | 匹配字符串的开始 | ^Hello | 匹配以“Hello”开头的字符串 |
$ | 匹配字符串的结束 | world!$ | 匹配以“world!”结尾的字符串 |
四、来看几个实际例子
现在我们把上面的规则组合起来!
-
匹配手机号(中国大陆简单版)
-
规则: 以1开头,第二位是3/4/5/7/8/9,后面跟着9位数字。
-
正则:
^1[345789]\d{9}$
-
分解:
^1
: 字符串必须以“1”开头。[345789]
: 紧接着是3,4,5,7,8,9中的任意一个。\d{9}
: 再紧接着是9个数字。
$
: 然后字符串就结束了。
-
-
匹配邮箱(简单版)
- 规则: 类似
xxx@xxx.xxx
的格式。 - 正则:
^\w+@\w+\.\w+$
- 分解:
^\w+
: 开头是1个或多个字母数字下划线(用户名)。@
: 紧接着一个“@”符号。\w+
: 又是1个或多个字母数字下划线(邮箱服务商,如gmail)。\.
: 紧接着一个真正的点号(.
在正则里是特殊符号,用\.
转义)。\w+$
: 以1个或多个字母数字下划线结尾(域名,如com)。
- 规则: 类似
-
提取日志中的日期
- 文本:
“2023-10-27 12:35:01 [INFO] User logged in”
- 正则:
\d{4}-\d{2}-\d{2}
- 结果: 匹配到
“2023-10-27”
- 文本:
五、如何开始练习和使用?
- 在线工具:强烈推荐! 在浏览器里打开一个正则在线测试网站(如 regex101.com 或 regexr.com),把你的文本和写的正则规则放进去,它会实时高亮显示匹配结果,还有非常详细的解释,是学习神器!
- 文本编辑器:VS Code, Sublime Text, Notepad++ 等都支持在搜索框里使用正则表达式。
- 编程语言:几乎所有主流编程语言(Python, JavaScript, Java, Go等)都内置了正则表达式库,学会基础语法后,就可以在代码中调用了。
总结给小白的学习建议:
- 别怕:它看起来像乱码,但其实逻辑清晰。
- 分解:遇到复杂的正则,像我们上面一样,把它拆成一小块一小块理解。
- 多练:从最简单的
a.b
,\d+
开始,在在线工具上自己敲一敲,改一改,看看效果。 - 不求甚解:先掌握最常用的(本文介绍的这些足以解决70%的问题),不需要一次性记住所有规则。用到的时候再查表即可。