MySQL 正则匹配的语法范围
MySQL 提供正则运算符用于条件判断,语义是部分匹配:只要字段值中包含符合模式的内容就为真,不需要整串相符。语法范围与版本密切相关,较新版本换用了新的正则引擎,支持面明显扩大;更早版本的实现接近扩展正则的子集,简写字符类等写法不可用。写跨版本都能跑的语句前,先确认实际版本。
基本信息
| 运算符形式 | 两种写法等价,可作为条件表达式的一部分使用 |
|---|---|
| 匹配语义 | 部分匹配,含子串即真,整串相符需要自行加锚点 |
| 版本影响 | 较新版本更换引擎后语法与 Unicode 支持范围改变 |
| 比较规则 | 大小写敏感性与字符集由字段的排序规则决定,可用字节比较强制区分 |
典型使用场景
- 数据质量巡检:找出格式不符合约定的记录,例如电话与编码字段
- 临时排查:在运维查询中快速筛选形如某模式的记录
- 规则校验:与约束配合,在写入前做一次形状检查
- 报表口径核对:对比两套系统中同类字段的格式差异
- 迁移前评估:统计待迁移数据中不符合目标格式的比例
查询写法与边界
查询写法与边界
-- 部分匹配:只要包含数字即命中
SELECT id FROM users WHERE phone REGEXP '[0-9]';
-- 整串匹配:两端加锚点,否则前缀后缀任意内容都会通过
SELECT id FROM users WHERE phone REGEXP '^[0-9]{11}$';
-- 排序规则影响大小写:不区分大小写的列默认会忽略大小写
SELECT 'Abc' REGEXP 'abc' AS ci_result; -- 结果取决于排序规则
SELECT BINARY 'Abc' REGEXP BINARY 'abc'; -- 强制字节比较,区分大小写
-- NULL 参与运算时结果为 NULL,需要显式处理
SELECT id FROM users WHERE phone IS NOT NULL AND phone REGEXP '^1';
-- 字符串字面量还有一层转义:反斜杠要写两次
SELECT 'a1' REGEXP '[0-9]' AS ok;语义与限制
| 项目 | 说明 | 注意 |
|---|---|---|
| 匹配范围 | 字段值任意位置 | 整串校验必须加锚点 |
| 大小写 | 由排序规则决定 | 换用字节比较可强制区分 |
| 简写字符类 | 视版本而定 | 跨版本脚本改用显式区间 |
| 索引使用 | 普通索引难以命中 | 先用其他条件缩小候选集 |
| 空值 | 结果为 NULL | 条件里要显式排除空值 |
正则条件通常无法使用普通索引,大数据表上把它放在过滤条件的第一位会退化成全表扫描;实践上先用等值与范围条件缩小候选集,再用正则做最终筛选。
层级转义是这里的常见错误来源:语句里的字符串字面量会解释一次反斜杠,正则引擎再解释一次,涉及简写字符类时需要用双反斜杠表达,涉及具体行为时以目标版本文档为准。