oracle 数据库sql高手来看看,如何纵向转横向

oracle 数据库sql高手来看看,如何纵向转横向,第1张

假设表有A,B两列,代码如下

select A,LISTAGG(B, ',') WITHIN GROUP(ORDER BY B) B from table group by A

上面SQL文可将B列横向输出,以逗号分割,输出顺序按B的值升序排列

1 建立数据透视表(图)的目的数据透视表能帮助用户分析、组织数据。利用它可以很快地从不同角度对数据进行分类汇兑。首先应该明确的是:不是所有工作表都有建立数据透视表(图)的必要。记录数量众多、以流水帐形式记录、结构复杂的工作表,为了,将其中的一些内在规律显现出来,可将工作表重新组合并添加算法。即,建立数据透视表(图)。例如,有一张工作表,是一个大公司员工(姓名、性别、出生年月、所在部门、工作时间、政治面貌、学历、技术职称、任职时间、毕业院校、毕业时间等)信息一览表,不但,字段(列)多,且记录(行)数众多。为此,需要建立数据透视表,以便将一些内在规律显现出来。2 创建数据透视表⑴将光标移入需建立数据透视表的工作表中,然后单击"数据"·"数据透视表和图表报告"。⑵"数据透视表和数据透视图向导-3步骤1"对话框上,单击"下一步"(选用默认选项,“Microsoft Excel数据清单或数据库”)。⑶在"数据透视表和数据透视图向导-3步骤2"对话框上,“选定区域”框中,已经自动选定工作表的(整个)数据区域,单击"下一步"。⑷在"数据透视表和数据透视图向导-3步骤3"对话框上,选用默认选项:"新建工作表",在当前工作的左侧创建一个新工作表。这样做,可以保证原始数据的安全以及可利用性。单击"完成"后,一张新工作表-“数据表(下图所示)”即出现在当前工作的左侧。3 设置数据表中数据的关系31 数据表上,几个区域的设定方法1、“请将行字段拖至此处”(相当于“左端标题行”),将作为横向分类依据的字段,从“数据透视表”工具栏上拖至此处。例如,将“所在部门”字段拖至此处。2、“请将列字段拖至此处”(相当于“顶端标题行”),将作为纵向分类依据的字段,从“数据透视表”工具栏上拖至此处。拖至此处的字段是计数的“依据”。例如,将“性别”字段拖至此处,计数的依据就是“男”和“女”两项。3、“请将数据项拖至此处”(相当于“普通数据区”),将作为统计依据的字段,从“数据透视表”工具栏上拖至此处。拖入该区中的字段,Excel将用某种算法,对其进行计算,然后将计算结果(汇总数值)显示出来(如何设置算法见32)。4、“请将页字段拖至此处”,将作为分类显示(筛选)依据的字段,从“数据透视表”工具栏上拖至此处。可以将一个或多个字段拖至此处。此区域中的字段是分类筛选的“首要”条件。例如,将“政治面貌”字段拖至此处,然后在其中,选择“党员”,则下方表格中,只统计“党员”有关的情况。提示:“顶端标题行”和“页字段”区中,均可有多个字段。32 透视分析数据改变透视表内部的透视关系,从不同的角度查看数据之间的内在关系。主要包括:改变透视关系、添加或删除项目以及数据更新1、改变透视关系更改各区域中的放置字段,或改变字段的分组条件即可以改变透视关系。添加字段的方法上面已经介绍过了,删除方法,是将需删除字段拖出数据表区域即可。改变字段分组条件的方法:单击字段名右侧的三角形按钮,然后单击下拉式列表菜单上的相应条件2、改变统计字段的算法双击透视表左上角的统计字段名,打开”数据透视表字段“对话框(右图)。在“汇总方式”框内,选定所需的算法,然后单击“确定”。提示:对日期型字段求和时,以1990年1月1日起算。3、透视表的更新若原工作表中的数据(含标题行-字段名)更改后,透视表作相应更新的方法:默认情况下,当重新打开工作薄时,透视表数据将自动更新。在不重新打开工作薄的情况下,在原工作表的数据更改后,在透视表中单击“数据透视表”工具栏上的“更新数据”按钮即可。提示:普通数据更改后,单击“更新数据”按钮后,即可完成更新。若更改了已经拖入透视表中的字段名,则该字段将从透视中删除,需要重新添加。4 透视图表将透视表制作成透视图表的方法是:单击“数据透视表”工具栏上的“图表向导”即可生成一张图表(位于左侧的新工作表上)。透视图表的编辑方法,与普通图表相似。

给你一个最长见的例子:普通行列转换

问题:假设有张学生成绩表(tb)如下:

姓名 课程 分数

张三 语文 74

张三 数学 83

张三 物理 93

李四 语文 74

李四 数学 84

李四 物理 94

想变成(得到如下结果):

姓名 语文 数学 物理

---- ---- ---- ----

李四 74 84 94

张三 74 83 93

-------------------

/

create table tb(姓名 varchar(10) , 课程 varchar(10) , 分数 int)

insert into tb values('张三' , '语文' , 74)

insert into tb values('张三' , '数学' , 83)

insert into tb values('张三' , '物理' , 93)

insert into tb values('李四' , '语文' , 74)

insert into tb values('李四' , '数学' , 84)

insert into tb values('李四' , '物理' , 94)

go

--SQL SERVER 2000 静态SQL,指课程只有语文、数学、物理这三门课程。(以下同)

select 姓名 as 姓名 ,

max(case 课程 when '语文' then 分数 else 0 end) 语文,

max(case 课程 when '数学' then 分数 else 0 end) 数学,

max(case 课程 when '物理' then 分数 else 0 end) 物理

from tb

group by 姓名

--SQL SERVER 2000 动态SQL,指课程不止语文、数学、物理这三门课程。(以下同)

declare @sql varchar(8000)

set @sql = 'select 姓名 '

select @sql = @sql + ' , max(case 课程 when ''' + 课程 + ''' then 分数 else 0 end) [' + 课程 + ']'

from (select distinct 课程 from tb) as a

set @sql = @sql + ' from tb group by 姓名'

exec(@sql)

--SQL SERVER 2005 静态SQL。

select from (select from tb) a pivot (max(分数) for 课程 in (语文,数学,物理)) b

--SQL SERVER 2005 动态SQL。

declare @sql varchar(8000)

select @sql = isnull(@sql + ',' , '') + 课程 from tb group by 课程

exec ('select from (select from tb) a pivot (max(分数) for 课程 in (' + @sql + ')) b')

---------------------------------

/

问题:在上述结果的基础上加平均分,总分,得到如下结果:

姓名 语文 数学 物理 平均分 总分

---- ---- ---- ---- ------ ----

李四 74 84 94 8400 252

张三 74 83 93 8333 250

/

--SQL SERVER 2000 静态SQL。

select 姓名 姓名,

max(case 课程 when '语文' then 分数 else 0 end) 语文,

max(case 课程 when '数学' then 分数 else 0 end) 数学,

max(case 课程 when '物理' then 分数 else 0 end) 物理,

cast(avg(分数10) as decimal(18,2)) 平均分,

sum(分数) 总分

from tb

group by 姓名

--SQL SERVER 2000 动态SQL。

declare @sql varchar(8000)

set @sql = 'select 姓名 '

select @sql = @sql + ' , max(case 课程 when ''' + 课程 + ''' then 分数 else 0 end) [' + 课程 + ']'

from (select distinct 课程 from tb) as a

set @sql = @sql + ' , cast(avg(分数10) as decimal(18,2)) 平均分 , sum(分数) 总分 from tb group by 姓名'

exec(@sql)

--SQL SERVER 2005 静态SQL。

select m , n平均分 , n总分 from

(select from (select from tb) a pivot (max(分数) for 课程 in (语文,数学,物理)) b) m,

(select 姓名 , cast(avg(分数10) as decimal(18,2)) 平均分 , sum(分数) 总分 from tb group by 姓名) n

where m姓名 = n姓名

--SQL SERVER 2005 动态SQL。

declare @sql varchar(8000)

select @sql = isnull(@sql + ',' , '') + 课程 from tb group by 课程

exec ('select m , n平均分 , n总分 from

(select from (select from tb) a pivot (max(分数) for 课程 in (' + @sql + ')) b) m ,

(select 姓名 , cast(avg(分数10) as decimal(18,2)) 平均分 , sum(分数) 总分 from tb group by 姓名) n

where m姓名 = n姓名')

drop table tb

------------------

------------------

/

问题:如果上述两表互相换一下:即表结构和数据为:

姓名 语文 数学 物理

张三 748393

李四 748494

想变成(得到如下结果):

姓名 课程 分数

---- ---- ----

李四 语文 74

李四 数学 84

李四 物理 94

张三 语文 74

张三 数学 83

张三 物理 93

--------------

/

create table tb(姓名 varchar(10) , 语文 int , 数学 int , 物理 int)

insert into tb values('张三',74,83,93)

insert into tb values('李四',74,84,94)

go

--SQL SERVER 2000 静态SQL。

select from

(

select 姓名 , 课程 = '语文' , 分数 = 语文 from tb

union all

select 姓名 , 课程 = '数学' , 分数 = 数学 from tb

union all

select 姓名 , 课程 = '物理' , 分数 = 物理 from tb

) t

order by 姓名 , case 课程 when '语文' then 1 when '数学' then 2 when '物理' then 3 end

--SQL SERVER 2000 动态SQL。

--调用系统表动态生态。

declare @sql varchar(8000)

select @sql = isnull(@sql + ' union all ' , '' ) + ' select 姓名 , [课程] = ' + quotename(Name , '''') + ' , [分数] = ' + quotename(Name) + ' from tb'

from syscolumns

where name! = N'姓名' and ID = object_id('tb') --表名tb,不包含列名为姓名的其它列

order by colid asc

exec(@sql + ' order by 姓名 ')

--SQL SERVER 2005 动态SQL。

select 姓名 , 课程 , 分数 from tb unpivot (分数 for 课程 in([语文] , [数学] , [物理])) t

--SQL SERVER 2005 动态SQL,同SQL SERVER 2000 动态SQL。

--------------------

/

问题:在上述的结果上加个平均分,总分,得到如下结果:

姓名 课程 分数

---- ------ ------

李四 语文 7400

李四 数学 8400

李四 物理 9400

李四 平均分 8400

李四 总分 25200

张三 语文 7400

张三 数学 8300

张三 物理 9300

张三 平均分 8333

张三 总分 25000

------------------

/

select from

(

select 姓名 as 姓名 , 课程 = '语文' , 分数 = 语文 from tb

union all

select 姓名 as 姓名 , 课程 = '数学' , 分数 = 数学 from tb

union all

select 姓名 as 姓名 , 课程 = '物理' , 分数 = 物理 from tb

union all

select 姓名 as 姓名 , 课程 = '平均分' , 分数 = cast((语文 + 数学 + 物理)10/3 as decimal(18,2)) from tb

union all

select 姓名 as 姓名 , 课程 = '总分' , 分数 = 语文 + 数学 + 物理 from tb

) t

order by 姓名 , case 课程 when '语文' then 1 when '数学' then 2 when '物理' then 3 when '平均分' then 4 when '总分' then 5 end

drop table tb

select 'enkey' enkey,

cast(sum(case when tenkey = 'a' then 1 else 0 end) as varchar) a,

cast(sum(case when tenkey = 'b' then 2 else 0 end) as varchar) b,

cast(sum(case when tenkey = 'c' then 3 else 0 end) as varchar) c

from (select enkey,listkey from indexlists where enkey in('M','A','XS','YS','TZ') ) t

union all

select 'listkey','a','b','c'

以上就是关于oracle 数据库sql高手来看看,如何纵向转横向全部的内容,包括:oracle 数据库sql高手来看看,如何纵向转横向、怎样用excel图表功能同时进行横向和纵向的数据分析、sql中怎么让结果集横向显示等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址:https://54852.com/sjk/9739511.html

(0)
打赏 微信扫一扫微信扫一扫 支付宝扫一扫支付宝扫一扫
上一篇 2023-05-01
下一篇2023-05-01

发表评论

登录后才能评论

评论列表(0条)

    保存