转:MSSQL SERVER行转列 列转行
- SQL Server中行列转换 Pivot UnPivot
- PIVOT用于将列值旋转为列名(即行转列),在SQL Server 2000可以用聚合函数配合CASE语句实现
- PIVOT的一般语法是:PIVOT(聚合函数(列) FOR 列 in (…) )AS P
- 完整语法:
- table_source
- PIVOT(
- 聚合函数(value_column)
- FOR pivot_column
- IN(<column_list>)
- )
- UNPIVOT用于将列明转为列值(即列转行),在SQL Server 2000可以用UNION来实现
- 完整语法:
- table_source
- UNPIVOT(
- value_column
- FOR pivot_column
- IN(<column_list>)
- )
- 注意:PIVOT、UNPIVOT是SQL Server 2005 的语法,使用需修改数据库兼容级别
- 在数据库属性->选项->兼容级别改为 90
- 典型实例
- 一、行转列
- 1、建立表格
- ifobject_id('tb')isnotnulldroptabletb
- go
- createtabletb(姓名varchar(10),课程varchar(10),分数int)
- insertintotbvalues('张三','语文',74)
- insertintotbvalues('张三','数学',83)
- insertintotbvalues('张三','物理',93)
- insertintotbvalues('李四','语文',74)
- insertintotbvalues('李四','数学',84)
- insertintotbvalues('李四','物理',94)
- go
- select*fromtb
- go
- 姓名 课程 分数
- ---------- ---------- -----------
- 张三 语文 74
- 张三 数学 83
- 张三 物理 93
- 李四 语文 74
- 李四 数学 84
- 李四 物理 94
- 2、使用SQL Server 2000静态SQL
- --c
- select姓名,
- max(case课程when'语文'then分数else0end)语文,
- max(case课程when'数学'then分数else0end)数学,
- max(case课程when'物理'then分数else0end)物理
- fromtb
- groupby姓名
- 姓名 语文 数学 物理
- ---------- ----------- ----------- -----------
- 李四 74 84 94
- 张三 74 83 93
- 3、使用SQL Server 2000动态SQL
- --SQL SERVER 2000动态SQL,指课程不止语文、数学、物理这三门课程。(以下同)
- --变量按sql语言顺序赋值
- declare@sqlvarchar(500)
- set@sql='select姓名'
- select@sql=@sql+',max(case课程when '''+课程+''' then分数else 0 end)['+课程+']'
- from(selectdistinct课程fromtb)a--同from tb group by课程,默认按课程名排序
- set@sql=@sql+' from tb group by姓名'
- exec(@sql)
- --使用isnull(),变量先确定动态部分
- declare@sqlvarchar(8000)
- select@sql=isnull(@sql+',','')+' max(case课程when '''+课程+''' then分数else 0 end) ['+课程+']'
- from(selectdistinct课程fromtb)asa
- set@sql='select姓名,'+@sql+' from tb group by姓名'
- exec(@sql)
- 姓名 数学 物理 语文
- ---------- ----------- ----------- -----------
- 李四 84 94 74
- 张三 83 93 74
- 4、使用SQL Server 2005静态SQL
- select*fromtb pivot(max(分数)for课程in(语文,数学,物理))a
- 5、使用SQL Server 2005动态SQL
- --使用stuff()
- declare@sqlvarchar(8000)
- set@sql='' --初始化变量@sql
- select@sql=@sql+','+课程fromtbgroupby课程--变量多值赋值
- set@sql=stuff(@sql,1,1,'')--去掉首个','
- set@sql='select * from tb pivot (max(分数) for课程in ('+@sql+'))a'
- exec(@sql)
- --或使用isnull()
- declare@sqlvarchar(8000)
- –-获得课程集合
- select@sql=isnull(@sql+',','')+课程fromtbgroupby课程
- set@sql='select * from tb pivot (max(分数) for课程in ('+@sql+'))a'
- exec(@sql)
- 二、行转列结果加上总分、平均分
- 1、使用SQL Server 2000静态SQL
- --SQL SERVER 2000静态SQL
- select姓名,
- max(case课程when'语文'then分数else0end)语文,
- max(case课程when'数学'then分数else0end)数学,
- max(case课程when'物理'then分数else0end)物理,
- sum(分数)总分,
- cast(avg(分数*1.0)asdecimal(18,2))平均分
- fromtb
- groupby姓名
- 姓名 语文 数学 物理 总分 平均分
- ---------- ----------- ----------- ----------- -----------
- 李四 74 84 94 252 84.00
- 张三 74 83 93 250 83.33
- 2、使用SQL Server 2000动态SQL
- --SQL SERVER 2000动态SQL
- declare@sqlvarchar(500)
- set@sql='select姓名'
- select@sql=@sql+',max(case课程when '''+课程+''' then分数else 0 end)['+课程+']'
- from(selectdistinct课程fromtb)a
- set@sql=@sql+',sum(分数)总分,cast(avg(分数*1.0) as decimal(18,2)) 平均分from tb group by姓名'
- exec(@sql)
- 3、使用SQL Server 2005静态SQL
- selectm.*,n.总分,n.平均分
- from
- (select*fromtb pivot(max(分数)for课程in(语文,数学,物理))a)m,
- (select姓名,sum(分数)总分,cast(avg(分数*1.0)asdecimal(18,2))平均分
- fromtb
- groupby姓名)n
- wherem.姓名=n.姓名
- 4、使用SQL Server 2005动态SQL
- --使用stuff()
- --
- declare@sqlvarchar(8000)
- set@sql='' --初始化变量@sql
- select@sql=@sql+','+课程fromtbgroupby课程--变量多值赋值
- --同select @sql = @sql + ','+课程from (select distinct课程from tb)a
- set@sql=stuff(@sql,1,1,'')--去掉首个','
- set@sql='select m.* , n.总分,n.平均分from
- (select * from (select * from tb) a pivot (max(分数) for课程in ('+@sql+')) b) m ,
- (select姓名,sum(分数)总分, cast(avg(分数*1.0) as decimal(18,2))平均分from tb group by姓名) n
- where m.姓名= n.姓名'
- exec(@sql)
- --或使用isnull()
- declare@sqlvarchar(8000)
- select@sql=isnull(@sql+',','')+课程fromtbgroupby课程
- set@sql='select m.* , n.总分,n.平均分from
- (select * from (select * from tb) a pivot (max(分数) for课程in ('+
- @sql+')) b) m ,
- (select姓名,sum(分数)总分, cast(avg(分数*1.0) as decimal(18,2))平均分from tb group by姓名) n
- where m.姓名= n.姓名'
- exec(@sql)
- 二、列转行
- 1、建立表格
- ifobject_id('tb')isnotnulldroptabletb
- go
- createtabletb(姓名varchar(10),语文int,数学int,物理int)
- insertintotbvalues('张三',74,83,93)
- insertintotbvalues('李四',74,84,94)
- go
- select*fromtb
- go
- 姓名 语文 数学 物理
- ---------- ----------- ----------- -----------
- 张三 74 83 93
- 李四 74 84 94
- 2、使用SQL Server 2000静态SQL
- --SQL SERVER 2000静态SQL。
- select*from
- (
- select姓名,课程='语文',分数=语文fromtb
- unionall
- select姓名,课程='数学',分数=数学fromtb
- unionall
- select姓名,课程='物理',分数=物理fromtb
- ) t
- orderby姓名,case课程when'语文'then1when'数学'then2when'物理'then3end
- 姓名 课程 分数
- ---------- ---- -----------
- 李四 语文 74
- 李四 数学 84
- 李四 物理 94
- 张三 语文 74
- 张三 数学 83
- 张三 物理 93
- 2、使用SQL Server 2000动态SQL
- --SQL SERVER 2000动态SQL。
- --调用系统表动态生态。
- declare@sqlvarchar(8000)
- select@sql=isnull(@sql+' union all ','')+' select姓名, [课程]='
- +quotename(Name,'''')+' , [分数] = '+quotename(Name)+' from tb'
- fromsyscolumns
- whereName!='姓名'andID=object_id('tb')--表名tb,不包含列名为姓名的其他列
- orderbycolid
- exec(@sql+' order by姓名')
- go
- 3、使用SQL Server 2005静态SQL
- --SQL SERVER 2005动态SQL
- select姓名,课程,分数fromtb unpivot (分数for课程in([语文],[数学],[物理])) t
- 4、使用SQL Server 2005动态SQL
- --SQL SERVER 2005动态SQL
- declare@sqlnvarchar(4000)
- select@sql=isnull(@sql+',','')+quotename(Name)
- fromsyscolumns
- whereID=object_id('tb')andNamenotin('姓名')
- orderbyColid
- set@sql='select姓名,[课程],[分数] from tb unpivot ([分数] for [课程] in('+@sql+'))b'
- exec(@sql)
转自:http://www.cnblogs.com/zhangzt/archive/2010/07/29/1787825.html
转:MSSQL SERVER行转列 列转行的更多相关文章
- SQL Server 行转列,列转行。多行转成一列
一.多行转成一列(并以","隔开) 表名:A 表数据: 想要的查询结果: 查询语句: SELECT name , value = ( STUFF(( SELECT ',' + va ...
- SQL Server 行转列,列转行
一.多行转成一列(并以","隔开) 表名:A 表数据: 想要的查询结果: 查询语句: SELECT name , value = ( STUFF(( SELECT ',' + va ...
- Sql server 中将数据行转列列转行(二)
老规矩,先弄一波测试数据,数据填充代码没有什么意义,先折叠起来: /* 第一步:创建临时表结构 */ CREATE TABLE #Student --创建临时表 ( StuName ), --学生名称 ...
- SQL SERVER将某一列字段中的某个值替换为其他的值 分类: MSSQL 2014-11-05 13:11 67人阅读 评论(0) 收藏
SQL SERVER将某一列字段中的某个值替换为其他的值 UPDATE 表名 SET 列名 = REPLACE(列名 ,'贷','袋') SQL SERVER"函数 replace 的参数 ...
- SQL Server自动化运维系列——关于邮件通知那点事(.Net开发人员的福利)
需求描述 在我们的生产环境中,大部分情况下需要有自己的运维体制,包括自己健康状态的检测等.如果发生异常,需要提前预警的,通知形式一般为发邮件告知. 邮件作为一种非常便利的预警实现方式,在及时性和易用性 ...
- Oracle 多行变一列的方法
多行变一列的方法有很多,觉得这个第一眼看懂了当时就用的这个办法. 情况是这样的.以下数据前几列是一样的,需要把VAT_VALUE_CHAR 的值放在同一行上. SELECT * FROM ps_vat ...
- 解读SQL Server 2014可更新列存储索引——存储机制
概述 SQL Server 2014被号称是微软数据库的一个革命性版本,其性能的提升的幅度是有史以来之最. 可更新的列存储索引作为SQL Server 2014的一个关键功能之一,在提升数据库的查询性 ...
- SQL Server中的标识列
一.标识列的定义以及特点 SQL Server中的标识列又称标识符列,习惯上又叫自增列. 该种列具有以下三种特点: .列的数据类型为不带小数的数值类型 .在进行插入(Insert)操作时,该列的值是由 ...
- SQL Server 2016:内存列存储索引
作者 Jonathan Allen,译者 谢丽 SQL Server 2016的一项新特性是可以在“内存优化表(Memory Optimized Table)”上添加“列存储索引(Columnstor ...
随机推荐
- InputSplit—>RecordReder—>map(key,value,context)的过程解析
上图首先描述了在TaskTracker端Task(MapTask.ReduceTask)的执行过程,MapTask(org.apache.hadoop.mapred)首先被TaskRunner调用,然 ...
- .net / java /安卓des加密互通
一 . C#.net /// <summary> /// 加密数据 /// </summary> /// <param name="Text"> ...
- select 下拉框的选中项的change事件
HTML文件 <span style="float: left;">类 型: <select id="type" class=& ...
- golang之archive/tar包的使用
原文地址:http://www.niu12.com/article/36 github地址:https://github.com/ZQCard/go_api_practice // tar包实现了文件 ...
- 【转载】struts应用在断网情况下启动报错解决办法(java/net/AbstractPlainSocketImpl.java:178:-1)
无意间struts应用在有网络的情况下启动正常,在断网的情况下启动报错,报错代码如下图所示: SEVERE: Exception starting filter struts2 Class: java ...
- C#拦截系统消息的方法-Application.AddMessageFilter
C#拦截系统消息的方法Application.AddMessageFilter Application.AddMessageFilter这个方法可以接收系统发出的消息: 首先定义一个类,继承IMess ...
- opengl中VAO,VBO,IBO用法小结【转】
http://cowboy.1988.blog.163.com/blog/static/751057982014380251300/ opengl中VAO,VBO,IBO用法小结 这三个玩意全面取代旧 ...
- BindVertexbuffer
stride 的意思是 inputstream.layout 的大小 比如 description是 pos uv normal stride 就是一组pos uv normal的大小 ns 里面 ...
- 【Hadoop】Hadoop MR 自定义排序
1.概念 2.代码示例 FlowSort package com.ares.hadoop.mr.flowsort; import java.io.IOException; import org.apa ...
- zabbix日志监控
一般情况下,日志最先反映出应用当前的问题,在海量日志里面找到我们异常记录,例如监控系统日志.nginx.Apache.业务日志,然后记录下来,并且根据情况报警. 1.日志监控项介绍 最主要的是监控日志 ...