第九章用正则表达式进行搜索
9.1正则表达式介绍
正则表达式是用来匹配文本的特殊的串(字符集合)。如果你想从一个文本文件中提取电话号码,可以使用正则表达式。如果你需要查找名字中间有数字的所有文件,可以 使用一个正则表达式。如果你想在一个文本块中找到所有重复的单词, 可以使用一个正则表达式。如果你想替换一个页面中的所有URL为这些 URL的实际HTML链接,也可以使用一个正则表达式(对于最后这个例子,或者是两个正则表达式)。
9.2使用MySQL正则表达式
9.2.1基本字符匹配
输入:
SELECT job_id
FROM employees
WHERE job_id REGEXP 'AD'
ORDER BY job_id;
输出:
说明:上面的语句用来检索包含文本AD的所有行。REGEXP后跟的内容作为正则表达式处理。
输入:
SELECT job_id
FROM employees
WHERE job_id REGEXP '.D'
ORDER BY job_id;
输出:
说明:这里使用了正则表达式.D,其中.是正则表达式语言中表示匹配任意一个字符的特殊字符。
输入:
SELECT job_id
FROM employees
WHERE job_id LIKE 'AD'
ORDER BY job_id;
输出:
说明:这就是LIKE和REGEXP之间的一个重要的差别,LIKE在匹配时,如果被匹配的文本在列植中出现,LIKE不会找到它,也不会返回其所在的行,而REGEXP则会找到它,也会返回其所在的行。匹配不区分大小写,区分大小写可以使用BINARY关键字。
9.2.2进行OR匹配
输入:
SELECT job_id
FROM employees
WHERE job_id REGEXP 'AD|IT'
ORDER BY job_id;
输出:
说明:|表示匹配其中之一,可以给出两个以上的OR条件。
9.2.3匹配几个字符之一
输入:
SELECT department_id
FROM employees
WHERE department_id REGEXP '[369]0'
ORDER BY department_id;
输出:
说明:匹配特定字符,可以使用一组用[和]括起来的字符来完成。这里的[369]代表匹配3或6或9,也可以写作[3|6|9]。
输入:
SELECT department_id
FROM employees
WHERE department_id REGEXP '3|6|90'
ORDER BY department_id;
输出:
这两者的差别在于如果写成3|6|90,实际的意思其实是匹配3或6或90,除非把字符|括在一个集合中,否则它将应用于整个串。
输入:
SELECT department_id
FROM employees
WHERE department_id REGEXP '[^3|6|9]0'
ORDER BY department_id;
输出:
说明:字符集合也可以被否定,只需要在集合的开始处放置一个^即可。
9.2.4匹配范围
输入:
SELECT department_id
FROM employees
WHERE department_id REGEXP '[2-3]0'
ORDER BY department_id;
输出:
说明:集合可用来定义要匹配的一个或多个字符,例如[0123456789],可简写为[0-9],且范围不限于完整的集合,如[1-3]和[6-9],范围也不一定是数字,如[a-z]匹配任意字母字符。
9.2.5匹配特殊字符
输入:
SELECT vend_name
FROM vendors
WHERE vend_name REGEXP '.'
ORDER BY vend_name;
输出:
说明:这里的.并非真正的.,而是代表任意一个字符的特殊字符,因此必须用\\作为前导。
输入:
SELECT vend_name
FROM vendors
WHERE vend_name REGEXP '\\.'
ORDER BY vend_name;
输出:
说明:正则表达式中的特殊字符都可以使用这种方式进行转义,\\也用来引用元字符。

多数正则表达式实现使用单个反斜杠转义特殊字符,但MySQL要求两个,一个MySQL自己解释,一个正则表达式库解释。为了匹配\本身,需要使用\\\。
9.2.6匹配字符类
为了方便工作,可以使用预定义的字符集,称为字符类。

9.2.7匹配多个实例
输入:
SELECT prod_name
FROM products
WHERE prod_name REGEXP '\\([0-9] sticks?\\)'
ORDER BY prod_name;
输出:
说明:在匹配重复出现时,可以使用正则表达式重复元字符来完成。

上例中正则表达式的含义为:\\(是在转义左括号,\\)是在转义右括号。[0-9]代表匹配的是0-9之间任意一个数字,stick是目标字符串中包含的值,?使得前面的s可选,即匹配前面的字符出现0次或1次。
输入:
SELECT prod_name
FROM products
WHERE prod_name REGEXP '[[:digit:]]{4}'
ORDER BY prod_name;
输出:
说明:[:digit:]会匹配任意数字,因而它是一个数字的集合。{4}确切地要求它前面的字符出现4次。所以该正则表达式其实在匹配连在一起的任意4位数字。
输入:
SELECT prod_name
FROM products
WHERE prod_name REGEXP '[0-9][0-9][0-9][0-9]'
ORDER BY prod_name;
输出:
说明:使用正则表达式匹配的方式不止一种。
9.2.8定位符
输入:
SELECT prod_name
FROM products
WHERE prod_name REGEXP '^[0-9\\.]'
ORDER BY prod_name;
输出:
说明:匹配特定位置的文本,可以使用定位符。

说明:^表示位于开头,[0-9]表示0-9中的任意一个数字,\\.表示匹配数字后加上小数点的文本。 用^开始表达式,$结束表达式,可以使REGEXP的作用和LIKE一样。
输入:
SELECT 'hello' REGEXP '[0-9]';
输出:
说明:可以在不使用数据库的情况下用SELECT来测试正则表达式,REGEXP的结果总是返回0(没有匹配)或1(匹配)。