Oracle使用正则表达式离不开这4个函数:
1 、regexp_like
2 、regexp_substr
3、 regexp_instr
4 、regexp_replace
2.1、REGEXP_SUBSTR
REGEXP_SUBSTR函数使用正则表达式来指定返回串的起点和终点。
语法:regexp_substr(source_string,pattern[,position[,occurrence[,match_parameter]]])
source_string:源串,可以是常量,也可以是某个值类型为串的列。
position:从源串开始搜索的位置。默认为1。
occurrence:指定源串中的第几次出现。默认值1.
match_parameter:文本量,进一步订制搜索,取值如下:
- 'i' 用于不区分大小写的匹配。
- 'c' 用于区分大小写的匹配。
- 'n' 允许将句点“.”作为通配符来匹配换行符。如果省略改参数,句点将不匹配换行符。
- 'm' 将源串视为多行。即将“^”和“$”分别看做源串中任意位置任意行的开始和结束,而不是看作整个源串的开始或结束。如果省略该参数,源串将被看作一行来处理。
- 如果取值不属于上述中的某个,将会报错。如果指定了多个互相矛盾的值,将使用最后一个值。如'ic'会被当做'c'处理。
- 省略该参数时:默认区分大小写、句点不匹配换行符、源串被看作一行。
例子:
- select regexp_substr('MY INFO: Anxpp,23,and boy','[[:digit:]]',1,2) from users;
结果:此处会返回3。注意这里同时用到了“[]”和“[:digit:]”。
2.2、REGEXP_INSTR
REGEXP_INSTR函数使用正则表达式返回搜索模式的起点和终点(整数)。如果没有发现匹配的值,将返回0。regexp_instr(source_string,pattern[,position[,occurrence[,return_option[,match_parameter]]]])
2.3、REGEXP_LIKE
通常使用REGEXP_LIKE进行模糊匹配。
2.4、REPLACE和REGEXP_REPLACE
REPLACE函数用于替换串中的某个值。
2.5、REGEXP_COUNT
REGEXP_COUNT函数返回在源串中出现的模式的次数,作为对REGEXP_INSTR函数的补充。
虽然COUNT是一个集合函数,操作的是行组,但是REGEXP_COUNT是单行函数,分别计算每一行。
值 | 描述 |
^ | 匹配一个字符串的开始。如果与“m” 的match_parameter一起使用,则匹配表达式中任何位置的行的开头。 |
$ | 匹配字符串的结尾。如果与“m” 的match_parameter一起使用,则匹配表达式中任何位置的行的末尾。 |
* | 匹配零个或多个。 |
+ | 匹配一个或多个出现。 |
? | 匹配零次或一次出现。 |
。 | 匹配任何字符,除了空。 |
| | 用“OR”来指定多个选项。 |
[] | 用于指定一个匹配列表,您尝试匹配列表中的任何一个字符。 |
[^] | 用于指定一个不匹配的列表,您尝试匹配除列表中的字符以外的任何字符。 |
() | 用于将表达式分组为一个子表达式。 |
{M} | 匹配m次。 |
{M,} | 至少匹配m次。 |
{M,N} | 至少匹配m次,但不多于n次。 |
n | n是1到9之间的数字。在遇到 n之前匹配在()内找到的第n个子表达式。 |
[..] | 匹配一个可以多于一个字符的整理元素。 |
[:] | 匹配字符类。 |
[==] | 匹配等价类。 |
d | 匹配一个数字字符。 |
D | 匹配一个非数字字符。 |
w | 匹配包括下划线的任何单词字符。 |
W | 匹配任何非单词字符。 |
s | 匹配任何空白字符,包括空格,制表符,换页符等等。 |
S | 匹配任何非空白字符。 |
A | 在换行符之前匹配字符串的开头或匹配字符串的末尾。 |
匹配字符串的末尾。 | |
*? | 匹配前面的模式零次或多次发生。 |
+? | 匹配前面的模式一个或多个事件。 |
?? | 匹配前面的模式零次或一次出现。 |
{N}? | 匹配前面的模式n次。 |
{N,}? | 匹配前面的模式至少n次。 |
{N,M}? | 匹配前面的模式至少n次,但不超过m次。 |
四. 量词
量词用来指定量词的前一个字符出现的次数。量词的形式主要有“?”、“*”、“+”、“{}”。量词在用于匹配字符串时,默认遵循贪婪原则。贪婪原则是指,尽可能多地匹配字符。例如:字符串“Function(p),(OK)”,如果使用正则表达式“.∗”进行匹配,则得到字符串“(p),(OK)” ,而非“(p)”;若欲得到“(p)”,则必须取消量词的贪婪原则,此时只需要为量词后追加另外一个数量词“?”即可。如上面的正则表达式应该改为“.∗?”。
五. 字符转义:
元字符在正则表达式中有特殊含义。如果需要使用其原义,则需要用到字符转义。字符转义使用字符“”来实现。其语法模式为:“”+元字符。例如,“.”表示普通字符“.”; “.doc”匹配字符串“.doc”;而普通字符“”需要使用“\”来表示。
六. 字符组.
字符组是指将模式中的某些部分作为一个整体。这样,量词可以来修饰字符组,从而提高正则表达式的灵活性。字符组通过()来实现.
许多编程语言中,可以利用“$1”、“$2”等来获取第一个、第二个字符组,即所谓的后向引用。在Oracle中,引用格式为“1”、“2”。
七. 正则表达式分支
可以利用“|”来创建多个正则表达式分支。例如,“d{4}|w{4}”可以看做两个正则表达式——“d{4}”和“w{4}”,匹配其中任何一个正则表达式的字符串都被认为匹配整个正则表达式。如果该字符串两个正则表达式分支都匹配,那么将被处理为匹配第一个正则表达式分支。
八. 字符类.
在Oracle中,正则表达式的用法与标准用法略有不同。这种不同主要体现在对于字符类的定义上。Orale中不使用字符“”与普通字符组合的形式来实现字符类,而是具有其特殊语法.
九. ORACLE中的四个正则表达式相关函数.
1. regexp_like(expression, regexp)
返回值为一个布尔值。如果第一个参数匹配第二个参数所代表的正则表达式,那么将返回真,否则将返回假。
举例: select * from people where regexp_like(name, '^J.*$');
相当于: select * from people where name like 'J%';
2. regexp_instr(expression, regexp, startindex, times)
返回找到的匹配字符串的位置.
参数startindex表示开始进行匹配比较的位置;参数times表示第几次匹配作为最终匹配结果。
举例: select regexp_instr('12.158', '.') position from dual;
regexp_instr('12.158', '.')用于获取第一个小数点的位置。
3. regexp_substr(expression, regexp)
返回第一个字符串参数中,与第二个正则表达式参数相匹配的子字符串。
举例: create table html(id integer, html varchar2(2000));
insert into html
values (1, '<a href="http://mail.google.com/2009/1009.html">mail link</a>');
表html中存储了HTML标签及内容。现欲从标签<a>中获得链接的url,那么可以利用regexp_substr()函数。
select id, regexp_substr(html, 'http[a-zA-Z0-9.:/]*') url from html;
4. regexp_replace(expression, regexp, replacement)
将expression中的按regexp匹配到的部分用replacement代替.
在参数replacement中,可以含有后向引用,以便将正则表达式中的字符组重新捕获。例如,某些国家和地区的日期格式可能为“MM/DD/YYYY”,那么可以利用regexp_replace()函数来转换日期格式。
select regexp_replace('09/29/2008', '^([0-9]{2})/([0-9]{2})/([0-9]{4})$', '3-1-2') replace
from dual;
注: 在进行正则表达式匹配时,还可以忽略字符大小写形式进行匹配.但是不能解除[[:upper:]]和[[:lower:]]的作用.
select * from people where regexp_like(name, 'or');
select * from people where regexp_like(name, 'or', 'i'); --‘i’表示忽略大小写
Oracle 数据库正则表达式中的 POSIX 元字符
元字符是具有特殊意义的字符,如通配符字符、重复字符、非匹配字符或一个字符范围。
可以在与函数匹配的模式中使用多个预定义的元字符符号。
符号 | 说明 |
*
|
匹配零个或多个匹配项 |
|
|
用于指定选择性匹配项的选择性运算符 |
^/$ |
匹配行的开头和结尾 |
[] |
用于匹配列表(匹配该列表中的任何表达式)的方括号表达式 |
[^exp] |
如果脱字符位于方括号内部,则对表达式取非。 |
{m} |
精确匹配 m 次 |
{m,n} |
至少匹配 m 次,但不超过 n 次 |
[: :] |
指定一个字符类并匹配该类中的任何字符 |
可以有四种不同的含义:(1) 表示其自身;(2) 引用下一个字符;(3) 引入一个运算符;(4) 不执行任何操作 |
|
+ |
匹配一个或多个匹配项 |
|
匹配零个或一个匹配项 |
. |
匹配所支持字符集中的任何字符(NULL 除外) |
() |
对表达式进行分组(视作一个子表达式) |
|
向后引用表达式 |
[==] |
指定等价类 |
[..] |
指定一个对照元素(如多字符元素) |
Perl 正则表达式扩展
除了 POSIX 标准以外,Oracle 还支持受 Perl 影响的常见元字符。如果您是一位生命科学开发人员,并使用 Perl 对大型 DNA 和蛋白质数据库中存储的生物信息数据进行模式分析,则可以使用 SQL 正则表达式直接支持数据,而无需中间层。这可以提供更高效的解决方案。为 Perl 兼容性而添加的元字符包括:
运算符 | 说明 |
d
|
匹配数字字符 |
D
|
匹配非数字字符 |
w |
匹配单词字符 |
W |
匹配非单词字符 |
s |
匹配空白字符 |
S |
匹配非空白字符 |
A |
仅匹配字符串的开头 |
仅匹配字符串的结尾或者行结尾之前 |
|
z |
仅匹配字符串的结尾 |
* |
匹配 0 次或更多次(非贪婪) |
+ |
匹配 1 次或更多次(非贪婪) |
? |
匹配 0 次或 1 次(非贪婪) |
{n} |
精确匹配 n 次(非贪婪) |
{n,} |
至少匹配 n 次(非贪婪) |
{n,m} |
至少匹配 n 次,但不超过 m 次(贪婪) |
2. |
检查 REGEXP_LIKE 函数的语法:
在该函数中: srcstr:是搜索值
要找到 PRODUCT_INFORMATION 表的 PRODUCT_NAME 列中名称包含 SSP/S、SSP/V、SSS/V 或 SSS/S 的所有产品,执行以下脚本: @relike.sql SELECT product_name
FROM oe.product_information
WHERE regexp_like (product_name, 'SS[PS]/[VS]');
|
3. |
REGEXP_INSTR 函数返回字符串中给定模式的位置。检查语法:
在该函数中: position:是搜索的起始位置
要搜索这些产品名称以找到第一个非字母字符(无论它是大写还是小写)的位置,执行以下脚本: @reinstr.sql COLUMN product_name FORMAT a45
COLUMN non_alpha FORMAT 9999999999
SELECT product_name, REGEXP_INSTR(product_name, '[^[:alpha:]]') non_alpha
FROM oe.product_information ;
请注意,[^[:<class>:]]表示一个字符类,并匹配该类中的任何字符;[:alpha:]匹配任何字母字符。在本示例中,您将通过使用 ^ 对该表达式取非。 |
4. |
REGEXP_SUBSTR 函数根据匹配项的模式返回给定字符串。检查语法:
在该函数中: position:是搜索的起始位置
您希望从 CUSTOMERS 表中提取电子邮件名,但是只提取位于瑞士的客户的电子邮件名。为此,您需要返回 CUST_EMAIL 列(该列位于 NLS_TERRITORY 为 Switzerland 的客户的 @ 符号前面)中的内容。执行以下脚本: @resubstr.sql SELECT REGEXP_SUBSTR(cust_email, '[^@]+')
FROM oe.customers
WHERE nls_territory = 'SWITZERLAND' ;
请注意,在本示例中,结果返回第一个没有 @ 符号的子字符串。 |
5. |
REGEXP_REPLACE 函数使用替换字符串所替换的模式的每一个匹配项来返回给定字符串。检查语法:
在该函数中: position:是搜索的起始位置
要返回 PRODUCT_INFORMATION 表的 CATALOG_URL 列中的信息,可以对该列执行完全扫描。但是,这将导致返回上百个行,这是因为它列出了多个目录域中的特定 HTML 页面位置。 在该示例中,您只想要查找单个域名本身,而不是它们所包含的低级页面。要查找不包含所有不必要信息的域名,使用 REGEXP_REPLACE 函数。执行以下脚本: @rereplace.sql SELECT UNIQUE REGEXP_REPLACE (catalog_url, 'http://([^/]+).*', '1')
FROM oe.product_information ;
|