正则表达式(Regular Expression)是一种强大的文本处理工具,在很多开发和应用环境都提供了支持,本文将介绍正则表达式在MySQL数据库的具体应用。
正则表达式的应用,关键在于模式(Pattern)的定义。模式中可以定义匹配的内容、匹配的数量、匹配的位置等要素。在MySQL数据库中,需要通过正则表达式模式作为文本查询条件时,可以使用regexp或rlike运算符,其基本应用格式如下:
<字段> regexp '<模式>'
代码中需要判断文本内容是否符合指定的模式时可以使用regexp_like(s,p)函数,其中,s为文本内容,p为指定的模式。当s符合p模式函数返回1,否则返回0;如果s或p为null则函数返回null。下面介绍模式的定义,并主要使用regexp_like()函数进行测试。
首先,定义模式时会使用一些特殊字符,如圆点(.)、星号(*)、问号(?)、加号(+)、中括号([和])、花括号({和})等,这些符号在模式定义有特殊的含义,称为正则表达式的元字符。在模式中如果需要匹配这些特殊字符,需要进行转义。比如,匹配加号时需要使用'\\+'定义;请注意,这里有两个外斜线(\\),实际进行了两次转义,第一个外斜线是MySQL文本转义符,用于对第二个外斜线进行转义,即'\\'在MySQL文本中表示一个外斜线;第一次转义后会得到'\+',此时才是模式的转义字符,最终转义为一个加号。简单点儿说,在MySQL中定义正则表达式模式时,转义字符需要使用两个外斜线。
在模式中,圆点(.)匹配任何一个字符,如下面的代码会返回1。
select regexp_like('abc', '.');
如果需要判断文本内容中是否包含圆点,则需要使用转义,如下面的代码会返回0。
select regexp_like('abc', '\\.');
这里可以修改regexp_like()函数第一个参数内容来观察执行结果。
使用中括号[和]可以定义字符集,用于匹配字符集中的任意一个字符,如下面的代码。
select regexp_like('Yes','[yn]');
代码会返回1,并且,只要文本中包含y、n、Y、N中的任何一个都会返回1。请注意,默认情况下模式中不区分字母大小写。本例,如果将'Yes'修改为不包含y、n、Y、N的内容则会返回0。
如果需要匹配不包含字符集内容的字符,可以在字符集中使用^开始,如下面的代码。
select regexp_like('Y','[^yn]');
本例,文本中只包含一个字母'Y',而模式定义为不包含y或n,执行代码会返回0。请注意,这里参数1的文本内容只要包含任何一个不是y或n的字符,执行代码都是返回1。
在集合中,还可以通过连接号(-)指定范围,如[0-9]表示数字、[a-z]表示英文小写字母、[A-Z]表示英文大写字母。如下面的代码。
select regexp_like('abc', '[0-9]');
执行代码会返回0,因为参数1的文本中没有包含数字0到9的任何一个字符。如果将模式修改为[^0-9]则表示任何一个非数字字符,执行结果会返回1。
需要匹配某类字符时,可以使用以下一些转义字符:
使用|定义多个规则,类似或(or)关系,如下面的代码。
select regexp_like('abc', '\d|[a-fA-F]');
本例模式用于匹配数字和字母a到f的大小写形式,即十六进制的字符,执行查询会显示1。这里,如果将模式中的'|'符号删除,则模式的含义就变为以1个数字开始,a到f字母在后的内容,文本'abc'中没有数字开始,则执行结果会返回0。
如果模式定义比较复杂,还可以使用圆括号定义为组,如下面的代码。
select regexp_like('abc', '(\d)|([a-fA-F])');
除了指定匹配的内容,还可以在匹配内容的后面定义匹配的次数,设置方法如下:
如下面的代码可以匹配11位数字。
select regexp_like('12345678910', '\\d{11}');
执行代码会返回1。可以修改参数1的文本内容,并观察执行结果。
模式中定义匹配的位置可以使用如下字符:
下面的代码通过\\b转义字符匹配完整的Jim。
select regexp_like('His Name is Jimmy.', '\\bJim\\b');
执行代码会显示0。模式'\\bJim\\b'会匹配完整的Jim,将模式修改为'\\bJimmy\\b'后会匹配参数1中的Jimmy,执行代码会返回1。
下面的代码演示^和$的应用。
select regexp_like('12345678910', '^1\\d{10}$');
模式中包含了2个部分,其中'^1'表示以数字1开始,'\\d{10}$'表示以10个数字结束。本例可修改参数1的文本内容并观察运行结果。
MySQL内置的正则表达式处理函数包括:
先来看各个参数的功能,如下表所示。
下面来看几个函数的应用实例。
regexp_like()函数已经使用多次,用于判断文本是否匹配指定的模式,下面来看match_type参数的应用。
select regexp_like('ABCD', 'a', 'c');
代码中指定match_type参数为'c',表示要区分字母大小写,此时文本中没有包含小写字母a,所以会返回0。删除'c'参数则不区分字母大小写,执行查询会返回1。
regexp_instr()函数可以判断匹配内容出现的位置,如下面的代码。
select regexp_instr('aaaa', 'a');
执行查询会返回1,即字母a在第一个位置出现。
下面的代码,指定从第3个字符开始匹配字母a。
select regexp_instr('aaaa', 'a',3);
执行查询会显示3。
下面的代码,指定从第一个位置开始匹配字母a,并返回第3次匹配结果的位置。
select regexp_instr('aaaa', 'a',1,3);
执行查询同样返回3。
regexp_replace()函数用于将文本中匹配的结果替换为新的内容,如下面的代码。
select regexp_replace('abcdefg', 'bcd', '***');
执行查询,会将参数1中的bcd替换为'***',结果返回'a***efg'。
regexp_substr()函数可以返回匹配的内容,用于观察匹配内容非常有效。下面的代码会返回bcd和1个数字的匹配结果。
select regexp_substr('abcd1abcd2abcd3', 'bcd\\d');
执行查询会返回bcd1。
下面的代码指定从第6个字符开始匹配,结果会显示bcd2。
select regexp_substr('abcd1abcd2abcd3', 'bcd\\d', 6);
下面的代码,指定从第1个字符开始匹配,并返回第3个匹配结果。
select regexp_substr('abcd1abcd2abcd3', 'bcd\\d', 1, 3);
执行查询会显示bcd3。
本文介绍了在MySQL数据库中使用正则表达式的基础知识,包括模式的定义、regexp_like()、regexp_instr()、regexp_replace()和regexp_substr()函数的使用等。
模式中可以定义匹配的内容、数量和位置等要素。人们常说,正则表达式的模式最非常难以阅读和理解,在一定程度上是有道理的;一个复杂的模式往往比较难以解读,正是因为这样,才需要更加熟练掌握模式各个要素的定义方法,只有通过大量的练习和测试才能写出符合要求的模式。