当前位置:  开发笔记 > 数据库 > 正文

Oracle转换表从行到列

如何解决《Oracle转换表从行到列》经验,为你挑选了1个好方法。

我有一个问题:

select vrec, valnum, valte from val_tb where  
recd in (select recd from rectb where setd = 17)
AND (vid = 3 OR vid = 26 OR vid = 28);

对于上面的结果,我得到:

vrec      valnum       valte
98945823  NULL         Total
98945823  NULL         06001
98945823  16.57        NULL 
98945824  NULL         Total
98945824  NULL         06005
98945824  0.36         NULL 

我想将其转换为:

98945823    06001   Total   16.57
98945824    06005   Total   0.36

即结合vrec的结果.

是否可以使用Oracle SQL执行此操作?



1> Lukasz Szozd..:

valte分值的一种方法是检查字符串是否仅包含数字(解决方案不好但应该起作用):

WITH cte( vrec,valnum, valte) AS
(
  SELECT 98945823 AS vrec,   NULL AS valnum,'Total' AS valte FROM dual
  UNION ALL SELECT 98945823, NULL,  '06001'      FROM dual
  UNION ALL SELECT 98945823, 16.57,  NULL        FROM dual
  UNION ALL SELECT 98945824, NULL,  'Total'      FROM dual
  UNION ALL SELECT 98945824, NULL,  '06005'      FROM dual
  UNION ALL SELECT 98945824, 0.36,  NULL         FROM dual
)
SELECT 
    vrec
   ,MAX(CASE WHEN REGEXP_LIKE(valte, '^[[:digit:]]*$') THEN valte ELSE NULL END)
   ,MAX(CASE WHEN NOT REGEXP_LIKE(valte, '^[[:digit:]]*$') THEN valte ELSE NULL END)
   ,MAX(valnum)
FROM cte
GROUP BY vrec;

SqlFiddleDemo

输出:

???????????????????????????????????????????????????????????
?   VREC    ? MAX(CASE...)  ? MAX(CASE...)  ? MAX(VALNUM) ?
???????????????????????????????????????????????????????????
? 98945823  ?        06001  ? Total         ? 16.57       ?
? 98945824  ?        06005  ? Total         ? 0.36        ?
???????????????????????????????????????????????????????????

对于您的案例交换cte硬编码值:

select vrec, valnum, valte from val_tb where  
recd in (select recd from rectb where setd = 17)
AND (vid = 3 OR vid = 26 OR vid = 28);

您的数据结构非常差,因此此解决方案只是解决方法.你应该真正改变底层结构.

推荐阅读
周扒pi
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有