SQL提取大括号之间的字符串(多个大括号可能在那里)

时间:2011-09-13 05:38:24

标签: sql oracle

我有以下列数据

NZ(abc_mode) / (NZ(bch_mode) + NZ(cdh_mode))

现在我需要一个查询来提取大括号NZ()内的字符串,无论是否使用SQL中的正则表达式。

输出应为

abc_mode
bch_mode
cdh_mode

1 个答案:

答案 0 :(得分:2)

这远非优雅,但会返回您想要的结果:

WITH t1
  AS (SELECT RTRIM(
              REGEXP_REPLACE('NZ(abc_mode) / (NZ(bch_mode) + NZ(cdh_mode)) ',
                            '([^[:alpha:]]{0,})(\({0,}NZ\()(([[:alpha:]]|\_){1,})(\){1,} {0,})', 
                            '\3,'), 
             ',') AS str
       FROM dual)
SELECT val
  FROM t1,
       XMLTABLE( '/root/e/text()'
                 PASSING xmltype( '<root><e>' || 
                                  REPLACE( t1.str, ',', '</e><e>' ) || 
                                  '</e></root>' )
                 COLUMNS val VARCHAR2( 10 ) PATH '/'
            )

请注意,我使用'NZ(abc_mode)/(NZ(bch_mode)+ NZ(cdh_mode))'作为文字,您需要将其替换为包含字符串的列名并替换“dual”使用包含列等的表。

因为这很乱,我会为你解决它: WITH子句设置SELECT

的数据
WITH t1
  AS (<SQL STATEMENT>)

REGEXP_REPLACE:

REGEXP_REPLACE('NZ(abc_mode) / (NZ(bch_mode) + NZ(cdh_mode)) ',
               '([^[:alpha:]]{0,})(\({0,}NZ\()(([[:alpha:]]|\_){1,})(\){1,} {0,})', 
               '\3,')

取字符串并搜索(括号中的模式部分):

(第1节)没有或多个非字母字符

(第2节)没有或多于括号的字符串“NZ(”

(第3节)一个或多个字母或下划线字符

(第4节)一个或多个右括号后跟无或多个空格

然后将匹配的模式替换为第3节中标识的内容,并添加逗号。

还在我身边吗? OK ......

然后修改REGEX的结果以删除尾随的逗号。

RTRIM(<regex_result>, ',')

所有这些的结果都是别名“str”(尽管你可能想给它一个更具描述性的名字)。

然后将“str”值拆分为主SELECT语句在逗号上的列。

希望这会有所帮助......