oracle unpivot 索引_oracle 11g中的pivot和unpivot转换操作

对于pivot和unpivot这个Oracle 11g的新功能一直就想总结一下,正好赶上论坛中有很多人会提问相关的问题,于是利用空闲时间翻译了一篇相关的网络文章。链接如下:

ITPuber:LuiseDalian翻译

时间:2012.11.29

1 Oracle 11g中的pivot和unpivot查询

转换查询包括将行转换成列(pivot)和将列转换成行(unpivot),从 而产生交叉表格式的结果。 转换是一项通用的技术,尤其对于报表来讲,正是由于该项技术使得多年来针对Oracle的不同版本,可以使用SQL语句产生转换查询的结果集。从 Oracle 11g开始,包含了显式的转换查询支持,即PIVOT和UNPIVOT关键字。这是对SELECT语句的扩展。

1.1 pivot

这里我们从pivot操作开始。大多数的开发者首先要熟悉转换数据:即多行被聚合,然后转换成列,每一列表示聚合数据的不同范围。语法:

除了新的pivot关键字外,可以看到3个新的pivot子句,描述如下:

 pivot_clause:定义被聚合的列(pivot是一种聚合操作)

 pivot_for_clause:定义被分组和转换的列。

 pivot_in_clause:定义pivot_for_clause子句中列的过滤器(例如使用值的范围来限制结果)。pivot_in_clause中每个值的聚合都将被转换成单独的列

1.1.1 一个简单的例子

这个例子是对pivot语法的简单的演示,使用scott.emp表,这里将通过department

和job来汇总salaries,然后转换对每个部门的汇总到它们各自的列上,在转换之前,先看一下基础数据

下面使用11g的语法来转换数据,对于每个job我们将sal的汇总,对每个部门使用单独一列。 可以看到对每个job按部门对sal的汇总已经变成了列,关于这个例子有几点需要注意,语法和结果:

 本例中的pivot_clause求sal列的和,如果需要可以指定多列和可选的别名。

 pivot操作执行隐式的GROUP BY,使用的列是没有出现在pivot_clause中的列(本例为job

和deptno)。大多数的转换查询都会在列的子集上进行操作,所以会使用存储视图、内联视图或子查询。

 这里的pivot_for_clause,表明我们只想转换deptno的聚合。

 这里的prvot_in_cluase,指明deptno值的范围,这里我们硬编码4个值的列表,这也是为什

么会产生4个转换列原因。如果省略别名,Oracle会使用pivot_in_clause中的值来产生转换后列的别名

如上所述,大多数的转换查询都在是列的特定的子集上来执行。像所有的聚合查询一样,额外列的出现会影响分组。这里只是通过在EMP表带有附加列的情况下进行转换查询,来确认这种影响。

在本例中,除了sal列,其余所有列都成了分组集,其中deptno为转换列。在本例中这个转换没有什么意义。

关于转换语法的非常有趣的一点是它在查询中的位置,即位于FROM和WHERE子句之间。 在下面的例子中,我们限制原来的转换查询在选择(通过添加谓词)出来的一些职位上进行。

上面的例子看起来好像是违反语感的,但是把谓词添加到pivot子句之前会产生语法错误。另外在我们的第1个例子中,我们是使用子查询部分(WITH语句)来定义基列的集合。我们可以使用内联视图(下例)或存储视图(后面的练习)来替代子查询。

1.1.2 给转换列指定别名

在前面的例子中,Oracle使用deptno列的值产生转换后列的名称,然而 我们可以给pivot_clause和pivot_in_clause中的一列或多列指定别名。通常Oracle将根据下面约定给转换列命名。 总结:就是pivot_in_clause中的列,如果指定别名就用别名,如果没有指定就用值;而pivot_cluaus中如果指定别名就连接到 pivot_in_cluase转换后的相应列的名称的后面,如果没有指定就不用。

5 / 41

下面将是这些别名选项的示例。我们已经做过没有任何别名的例子。为了简化起见,我们将输入数据集定义为视图。

给转换查询的所有元素指定别名。(Y, Y),Oracle将对应别名连接起来产生列名。

pivot_in_clause中的列不指定,pivot_clause中的列指定别名。(N, Y)

Oracle连接pivot_in_clause中的值和聚合列的别名产生列名。

只给

pivot_in_clause中的值指定别名。(Y,N),Oracle仅使用pivot_in_clause中的别名产生列名

总结:在所有的例子中pivot_in_clause用于所有的转换列的命名,不管我们是指定了值还是别名。因此,我们可以选择对哪些值指定别名。

1.1.3 转换多个列

目前为止,我们的例子都限制在一个聚合和一个转换列,然而我们可以定义多个。在下面的例子中将在pivot_clause中定义2个聚合,而对于deptno范围使用与前面的例子相同的值。新的聚合是对求和的薪水的计数。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值