REGEXP_SUBSTR 圆括号
REGEXP_SUBSTR round bracket
我想用 PL/SQL 将分号分隔的字符串分成多个部分。只要字符串中没有圆括号,REGEXP_SUBSTR 就可以正常工作。
示例:
select REGEXP_SUBSTR('A;B;C','[^(";")]+',1,1),
REGEXP_SUBSTR('A;B;C','[^(";")]+',1,2),
REGEXP_SUBSTR('A;B;C','[^(";")]+',1,3)
from dual;
预期的结果是:A B C
A;B(1);C 的结果应该是 A B(1) C 但我得到的是:A B 1
select REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,1),
REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,2),
REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,3)
from dual;
这意味着“(”被检测为分隔符,但我不明白这种行为。有人可以赐教吗?
[]
是一个 Multilingual Regular Expression Syntax 表示 "Bracket expression for specifying a matching list that should match any one of the expressions represented in the list. A nonmatching list expression begins with a circumflex (^) and specifies a list that matches any character except for the expressions represented in the list."
例如
select REGEXP_SUBSTR('"A";"B(1)";"C"','[^";"]+',1,1)
from dual;
将 return A B(1) C
其中 [^";"]+
认为 "
或 ;
作为分隔符
与您的示例类似,[^(";")]+
将 "
OR ;
OR (
OR )
作为分隔符,这与您的期望不符。
因此,对于您预期的输出,您可以尝试
select REGEXP_SUBSTR('A;B(1);C','[^;]+',1,1),
REGEXP_SUBSTR('A;B(1);C','[^;]+',1,2),
REGEXP_SUBSTR('A;B(1);C','[^;]+',1,3)
from dual;
我再一次爬上我的肥皂盒来警告人们使用 '[^;]+'
格式的正则表达式来解析分隔字符串的危险。悔改得救!它不处理 NULL 元素,并且会 return 意想不到的结果。有关详细信息和证明,请参阅 。请改用此格式,并在知道您的输出是准确的情况下高枕无忧:
注意第二个元素是 (NULL)
SQL> with tbl(str) as (
select 'A;;B(1);C' from dual
)
select regexp_substr(str, '(.*?)(;|$)', 1, level, NULL, 1)
from tbl
connect by level <= regexp_count(str, ';') + 1;
REGEXP_SU
---------
A
B(1)
C
SQL>
请注意元素 2 的 NULL returned,正如预期的那样。如果您使用正则表达式格式 '[^;]+'
并尝试获取第二个元素,您将得到 'B(1)'
这是不正确的,因为它是第三个元素:
不要使用:
SQL> with tbl(str) as (
2 select 'A;;B(1);C' from dual
3 )
4 select regexp_substr(str, '[^;]+', 1, level)
5 from tbl
6 connect by level <= regexp_count(str, ';') + 1;
REGEXP_SU
---------
A
B(1)
C
SQL>
仔细看,NULL在最后。想象一下所有不正确的报告。不要让其中之一成为你的!
我想用 PL/SQL 将分号分隔的字符串分成多个部分。只要字符串中没有圆括号,REGEXP_SUBSTR 就可以正常工作。
示例:
select REGEXP_SUBSTR('A;B;C','[^(";")]+',1,1),
REGEXP_SUBSTR('A;B;C','[^(";")]+',1,2),
REGEXP_SUBSTR('A;B;C','[^(";")]+',1,3)
from dual;
预期的结果是:A B C
A;B(1);C 的结果应该是 A B(1) C 但我得到的是:A B 1
select REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,1),
REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,2),
REGEXP_SUBSTR('A;B(1);C','[^(";")]+',1,3)
from dual;
这意味着“(”被检测为分隔符,但我不明白这种行为。有人可以赐教吗?
[]
是一个 Multilingual Regular Expression Syntax 表示 "Bracket expression for specifying a matching list that should match any one of the expressions represented in the list. A nonmatching list expression begins with a circumflex (^) and specifies a list that matches any character except for the expressions represented in the list."
例如
select REGEXP_SUBSTR('"A";"B(1)";"C"','[^";"]+',1,1)
from dual;
将 return A B(1) C
其中 [^";"]+
认为 "
或 ;
作为分隔符
与您的示例类似,[^(";")]+
将 "
OR ;
OR (
OR )
作为分隔符,这与您的期望不符。
因此,对于您预期的输出,您可以尝试
select REGEXP_SUBSTR('A;B(1);C','[^;]+',1,1),
REGEXP_SUBSTR('A;B(1);C','[^;]+',1,2),
REGEXP_SUBSTR('A;B(1);C','[^;]+',1,3)
from dual;
我再一次爬上我的肥皂盒来警告人们使用 '[^;]+'
格式的正则表达式来解析分隔字符串的危险。悔改得救!它不处理 NULL 元素,并且会 return 意想不到的结果。有关详细信息和证明,请参阅
注意第二个元素是 (NULL)
SQL> with tbl(str) as (
select 'A;;B(1);C' from dual
)
select regexp_substr(str, '(.*?)(;|$)', 1, level, NULL, 1)
from tbl
connect by level <= regexp_count(str, ';') + 1;
REGEXP_SU
---------
A
B(1)
C
SQL>
请注意元素 2 的 NULL returned,正如预期的那样。如果您使用正则表达式格式 '[^;]+'
并尝试获取第二个元素,您将得到 'B(1)'
这是不正确的,因为它是第三个元素:
不要使用:
SQL> with tbl(str) as (
2 select 'A;;B(1);C' from dual
3 )
4 select regexp_substr(str, '[^;]+', 1, level)
5 from tbl
6 connect by level <= regexp_count(str, ';') + 1;
REGEXP_SU
---------
A
B(1)
C
SQL>
仔细看,NULL在最后。想象一下所有不正确的报告。不要让其中之一成为你的!