ICode9

精准搜索请尝试: 精确搜索
首页 > 数据库> 文章详细

ORACLE逗号分割的字符串转多行(转载)

2021-01-12 09:32:17  阅读:283  来源: 互联网

标签:多行 EXE LEVEL VALUE 逗号 connect ORACLE REGEXP ID


分割单行数据

我们需要使用REGEXP_SUBSTRREGEXP_COUNT两个ORACLE函数

function REGEXP_SUBSTR(string, pattern, position, occurrence, modifier)
string:需要进行正则处理的字符串
pattern:进行匹配的正则表达式
position:起始位置,从第几个字符开始正则表达式匹配(默认为1)
occurrence:标识第几个匹配组,默认为1
modifier:模式(‘i’不区分大小写进行检索;‘c’区分大小写进行检索。默认为’c’)

function REGEXP_COUNT ( string, pattern [, position [, match_param]])
返回pattern 在string串中出现的次数。如果未找到匹配,则函数返回0。position 变量告诉Oracle 在源串的什么位置开始搜索。在开始位置之后每出现一次模式,都会使计数结果增加1。

SELECT REGEXP_SUBSTR('B00053,D00058,D00094', '[^,]+', 1, LEVEL) VALUE
  FROM DUAL
CONNECT BY LEVEL <= REGEXP_COUNT('B00053,D00058,D00094', '[^,]+')
  • 1
  • 2
  • 3

分割后结果如下:
在这里插入图片描述

分割多行数据

我们有三行初始数据
在这里插入图片描述

WITH TEMP AS
 (SELECT T.VALUE, T.COUNTS, T.EXE_ID
    FROM SC_MONIT_EXERESULT T
   INNER JOIN SYS_TASK_EXECUTE A
      ON T.EXE_ID = A.EXEC_ID
   WHERE FIELD_CODE = 'fundList'
     AND A.BUSIDATE = '20180604'
     AND VALUE = 'B00053,D00058,D00094')
SELECT REGEXP_SUBSTR(VALUE, '[^,]+', 1, LEVEL) VALUE,
       COUNTS,
       EXE_ID
  FROM TEMP
CONNECT BY LEVEL <= REGEXP_COUNT(VALUE, '[^,]+')
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

分割后数据变成了39行而不是9行!
问题出在使用connect by时,没有类似 id=prior pid的条件,而是 connect by rownum<xxx 或 connect by level<xxx 时,每一条记录都会作为自己或者其他记录的子节点,也就说,每一条记录的子节点就是表上所有的记录。而树的层数就是rownum(或是level)值。
假设表中有N条记录,则记F(N,l)为select id,level from t connect by level<l 的结果集数目。那么:
F ( N , 1 ) = N F(N,1)=NF(N,1)=N
F ( N , l ) = F ( N , l − 1 ) ∗ N + N F(N,l) = F(N,l-1)*N+NF(N,l)=F(N,l−1)∗N+N
l e v e l &lt; = 3 level&lt;=3level<=3 时,递归查询到的树状结构:
在这里插入图片描述
参考文章:深入理解connect by level

我们需要给树加上父子关系,用rownum作为PK列

WITH TEMP AS
 (SELECT T.VALUE, T.COUNTS, T.EXE_ID, ROWNUM ROWNUM1
    FROM SC_MONIT_EXERESULT T
   INNER JOIN SYS_TASK_EXECUTE A
      ON T.EXE_ID = A.EXEC_ID
   WHERE FIELD_CODE = 'fundList'
     AND A.BUSIDATE = '20180604'
     AND VALUE = 'B00053,D00058,D00094')
SELECT 'fundCode' FIELD_CODE,
       REGEXP_SUBSTR(VALUE, '[^,]+', 1, LEVEL) VALUE,
       COUNTS,
       EXE_ID
  FROM TEMP
CONNECT BY PRIOR ROWNUM1 = ROWNUM1
       AND LEVEL <= REGEXP_COUNT(VALUE, '[^,]+')
       AND PRIOR DBMS_RANDOM.VALUE() IS NOT NULL
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

PRIOR DBMS_RANDOM.VALUE() IS NOT NULL告诉ORACLE每次循环是不一样的,不然会报connect by死循环
最后得到的结果:
在这里插入图片描述

标签:多行,EXE,LEVEL,VALUE,逗号,connect,ORACLE,REGEXP,ID
来源: https://www.cnblogs.com/Kevin1002/p/14265391.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有