Oracle 行列转换(一) case行列转换思路简析

思路简析:

1° 准备测试数据:

drop table t purge;
create table t(a varchar2(10), b varchar2(10));
insert into t values('a1','b1');
insert into t values('a1','b2');
commit;

2° 进行行列转换的数据一般是”某一列”存在重复冗余的数据,如:

select * from t;

这里写图片描述

表t的列A中值a1存在重复,可以将a1作为基准,对a1所在的两行的列B的数值b1和b2做行列转换,行转列
因为列B的取值范围有两个b1和b2,因此行列转换后会生成两列,即两行转两列

3° 生成新列:

select a, b,
       case b when 'b1' then '第1个列值生成新第1列'
         else null
       end as b1,
       case b when 'b2' then '第2个列值生成新第2列'
         else null
       end as b2
  from t;

这里写图片描述

使用多个case函数对列B的列值进行匹配,将匹配到的相应列值转化成新列,行转列数据模式初显

4° case语法较为臃肿,使用decode函数进行改写:

select a, b,
       decode(b,'b1','第1个列值生成新第1列',null) as b1,
       decode(b,'b2','第2个列值生成新第2列',null) as b2
  from t;

5° 我们已经将B列列值展开成多列,因此剔除B列展示,然后先查看展开生成的第一列,观察特点:

select a, -- b,
       decode(b,'b1','第1个列值生成新第1列',null) as b1 -- ,
       -- decode(b,'b2','第2个列值生成新第2列',null) as b2
  from t;

这里写图片描述

此时不难发现,展开生成的第一列存在空值,意义不大,应该过滤掉,可以使用 where B1 is not null
但是该方法需要使用子查询,因为SQL执行顺序是先执行where后执行select

6° 另外一种方法是依据A列分组,对B1列进行聚合处理,因为B1是字符串,使用max或者min均可过滤掉空值:

select a, -- b,
       min(decode(b,'b1','第1个列值生成新第1列',null)) as b1 -- ,
       -- decode(b,'b2','第2个列值生成新第2列',null) as b2
  from t
  group by a;

这里写图片描述

7° 将所有展开列都依此处理,得出最后SQL:

select a, -- b,
       min(decode(b,'b1','第1个列值生成新第1列',null)) as b1,
       max(decode(b,'b2','第2个列值生成新第2列',null)) as b2
  from t
  group by a;

这里写图片描述

8° 简单总结:

字段值重复是行列转换的基础,如果不存在冗余数据列,则无法进行行列转换
行列转换的方法就是使用case或者decode对冗余数据列之外的其他列的列值进行展开
然后依据冗余数据列分组聚合,最后形成行列转换的功能

[TOC]

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值