oracle中的行列转换(一 列转行 pivot)

来源:互联网 发布:java面试项目介绍范文 编辑:程序博客网 时间:2024/05/17 03:33

在实际统计中,我们可能需要对统计的数据进行行列转换以达到我们想要的更便于分析查看对比的格式。例如:我们想要统计在一段时间(过去一年或一个月)所有客户在24小时的消费情况。对于结果我们更愿意让一行记录标识一个客户的24小时消费情况。下面我以oracle中的emp表为例,使用pivot列转行达到我们想要的效果。

select deptno, empjob, sum(sal) from emp group by deptno, empjob order by deptno, empjob

结果如下:

这里写图片描述

显然这样的结果并不便于我们观察各部门各职位的总薪资。我们可以使用pivot来实现:

select * from    (select deptno, empjob, sal from emp)  pivot(    sum(sal)  for empjob in (      'PRESIDENT' as PRESIDENT,      'MANAGER' as MANAGER,      'ANALYST' as ANALYST,      'CLERK' as CLERK,      'SALESMAN' as SALESMAN    )  ) order by deptno; 

结果如下:
这里写图片描述

我们可能不想自己手工输入empjob对应的值,可以使用plsql解决这个问题。

declare  str1 varchar2(200); str2 varchar2(500);beginselect LISTAGG( empjob,''',''') within group (order by  empjob) as str into str1  from  (select empjob from emp group by empjob);STR1 := ' '' '||str1 ||' '' ';str2 := 'select * from    (select deptno, empjob, sal from emp)  pivot(    sum(sal)  for empjob in (      '||str1||' )  ) order by deptno';DBMS_OUTPUT.PUT_LINE('str1:'||str1);DBMS_OUTPUT.PUT_LINE('str2'||str2);end;

输出结果为:

str1:' ANALYST','CLERK','MANAGER','PRESIDENT','SALESMAN ' str2:select * from  (select deptno, empjob, sal from emp)pivot(  sum(sal)  for empjob in (     'ANALYST','CLERK','MANAGER','PRESIDENT','SALESMAN'  )  ) order by deptno

注意:
str2执行后查询到的结果:

这里写图片描述

注意:类名称可能并不是我们期望的,注意修改列名称。

这时候我们就可以根据业务逻辑需求修改plsql或者存储过程等,创建相应的表或者视图,将查询到的数据放到表或视图,方便我们以后使用。

上面的例子是只有sum(sal)这一列的值,现在我们要解决的问题是:汇总各部门各职位的薪资总和和职员人数。

select * from  (select deptno, empjob, sal from emp)pivot(  sum(sal) as sal_sum, count(sal) as num   for empjob in (    'PRESIDENT' as PRESIDENT,      'MANAGER' as MANAGER,      'ANALYST' as ANALYST,      'CLERK' as CLERK,      'SALESMAN' as SALESMAN    )  ) order by deptno

结果如下:

这里写图片描述

0 0