SQL 列转行与行转列
Name Subject Result
张三 语文 74
张三 数学 83
张三 物理 93
李四 语文 74
李四 数学 84
李四 物理 94
*/
-------------------------------------------------------------------------
/*
想变成
姓名 语文 数学 物理
---------- ----------- ----------- -----------
李四 74 84 94
张三 74 83 93
*/
create table tb
(
Name varchar(10) ,
Subject varchar(10) ,
Result int
)
insert into tb(Name , Subject , Result) values('张三' , '语文' , 74)
insert into tb(Name , Subject , Result) values('张三' , '数学' , 83)
insert into tb(Name , Subject , Result) values('张三' , '物理' , 93)
insert into tb(Name , Subject , Result) values('李四' , '语文' , 74)
insert into tb(Name , Subject , Result) values('李四' , '数学' , 84)
insert into tb(Name , Subject , Result) values('李四' , '物理' , 94)
go
--静态SQL,指subject只有语文、数学、物理这三门课程。
select name 姓名,
max(case subject when '语文' then result else 0 end) 语文,
max(case subject when '数学' then result else 0 end) 数学,
max(case subject when '物理' then result else 0 end) 物理
from tb
group by name
/*
姓名 语文 数学 物理
---------- ----------- ----------- -----------
李四 74 84 94
张三 74 83 93
*/
--动态SQL,指subject不止语文、数学、物理这三门课程。
declare @sql varchar(8000)
set @sql = 'select Name as ' + '姓名'
select @sql = @sql + ' , max(case Subject when ''' + Subject + ''' then Result else 0 end) [' + Subject + ']'
from (select distinct Subject from tb) as a
set @sql = @sql + ' from tb group by name'
exec(@sql)
/*
姓名 数学 物理 语文
---------- ----------- ----------- -----------
李四 84 94 74
张三 83 93 74
*/
-------------------------------------------------------------------
/*加个平均分,总分
姓名 语文 数学 物理 平均分 总分
---------- ----------- ----------- ----------- -------------------- -----------
李四 74 84 94 84.00 252
张三 74 83 93 83.33 250
*/
--静态SQL,指subject只有语文、数学、物理这三门课程。
select name 姓名,
max(case subject when '语文' then result else 0 end) 语文,
max(case subject when '数学' then result else 0 end) 数学,
max(case subject when '物理' then result else 0 end) 物理,
case(avg(result*1.0) as decimal(18,2)) 平均分,
sum(result) 总分
from tb
group by name
/*
姓名 语文 数学 物理 平均分 总分
---------- ----------- ----------- ----------- -------------------- -----------
李四 74 84 94 84.00 252
张三 74 83 93 83.33 250
*/
--动态SQL,指subject不止语文、数学、物理这三门课程。
declare @sql1 varchar(8000)
set @sql1 = 'select Name as ' + '姓名'
select @sql1 = @sql1 + ' , max(case Subject when ''' + Subject + ''' then Result else 0 end) [' + Subject + ']'
from (select distinct Subject from tb) as a
set @sql1 = @sql1 + ' , cast(avg(result*1.0) as decimal(18,2)) 平均分,sum(result) 总分 from tb group by name'
exec(@sql1)
/*
姓名 数学 物理 语文 平均分 总分
---------- ----------- ----------- ----------- -------------------- -----------
李四 84 94 74 84.00 252
张三 83 93 74 83.33 250
*/
drop table tb
---------------------------------------------------------
---------------------------------------------------------
/*
如果上述两表互相换一下:即
姓名 语文 数学 物理
张三 74 83 93
李四 74 84 94
想变成
Name Subject Result
---------- ------- -----------
李四 语文 74
李四 数学 84
李四 物理 94
张三 语文 74
张三 数学 83
张三 物理 93
*/
create table tb1
(
姓名 varchar(10) ,
语文 int ,
数学 int ,
物理 int
)
insert into tb1(姓名 , 语文 , 数学 , 物理) values('张三',74,83,93)
insert into tb1(姓名 , 语文 , 数学 , 物理) values('李四',74,84,94)
select * from
(
select 姓名 as Name , Subject = '语文' , Result = 语文 from tb1
union all
select 姓名 as Name , Subject = '数学' , Result = 数学 from tb1
union all
select 姓名 as Name , Subject = '物理' , Result = 物理 from tb1
) t
order by name , case Subject when '语文' then 1 when '数学' then 2 when '物理' then 3 when '总分' then 4 end
--------------------------------------------------------------------
/*加个平均分,总分
Name Subject Result
---------- ------- --------------------
李四 语文 74.00
李四 数学 84.00
李四 物理 94.00
李四 平均分 84.00
李四 总分 252.00
张三 语文 74.00
张三 数学 83.00
张三 物理 93.00
张三 平均分 83.33
张三 总分 250.00
*/
select * from
(
select 姓名 as Name , Subject = '语文' , Result = 语文 from tb1
union all
select 姓名 as Name , Subject = '数学' , Result = 数学 from tb1
union all
select 姓名 as Name , Subject = '物理' , Result = 物理 from tb1
union all
select 姓名 as Name , Subject = '平均分' , Result = cast((语文 + 数学 + 物理)*1.0/3 as decimal(18,2)) from tb1
union all
select 姓名 as Name , Subject = '总分' , Result = 语文 + 数学 + 物理 from tb1
) t
order by name , case Subject when '语文' then 1 when '数学' then 2 when '物理' then 3 when '平均分' then 4when '总分' then 5 end
drop table tb1
SQL 列转行与行转列的更多相关文章
- SQL列转行,行转列实现
在工作中,大家可能会遇到一些SQL列转行.行转列的问题,恰好,我也遇到了,就在此记录一下.此处所用的是SQLServer2008R2. 行转列,列转行,都要预先知道要要处理多少数据,在此我就以三种方案 ...
- oracle 逗号分割,列转行,行转列
SQL代码 列转行 select REGEXP_SUBSTR(a.rolecode ,,l) rolecode from ( select 'a,aa,aaa' rolecode from dual ...
- Spark基于自定义聚合函数实现【列转行、行转列】
一.分析 Spark提供了非常丰富的算子,可以实现大部分的逻辑处理,例如,要实现行转列,可以用hiveContext中支持的concat_ws(',', collect_set('字段'))实现.但是 ...
- hive中的列转行和行转列
1.列转行 1.1 相关函数的说明: concat(string1,string,...) //连接括号内字符串,数量不限. concat_ws(separator,string1,string2,. ...
- SQL面试题之行转列
典型的课程表: mysql> select * from course; +----+------------+----------+------------+ | id | teacher_i ...
- Sql server 中将数据行转列列转行(二)
老规矩,先弄一波测试数据,数据填充代码没有什么意义,先折叠起来: /* 第一步:创建临时表结构 */ CREATE TABLE #Student --创建临时表 ( StuName ), --学生名称 ...
- sqlserver 行转列、字符串行转列、自动生产行转列脚本
行转列,老生常谈的问题.这里总结一下网上的方法. 1.生成测试数据: CREATE TABLE human( name ), --姓名 norm ), --指标 score INT , --分数 gr ...
- Sql server 中将数据行转列列转行(一)
在做一些数据分析与数据展示时,经常会遇到行转列,列转行的需求,今天就来总结下: 在开始之前,先来创建一个临时表,并且写入一些测试数据: /* 第一步:创建临时表结构 */ CREATE TABLE # ...
- SQL SERVER pivot(行转列),unpivot(列转行)
[pivot]行转列:多行变一列 假设学生成绩表Score1 Name Subject Score 小张 语文 88 小花 数学 89 小张 数学 90 Name 语文 数学 小花 null 89 小 ...
随机推荐
- POJ - 3660 Cow Contest(传递闭包)
题意: n个点,m条边. 若A 到 B的边存在,则证明 A 的排名一定在 B 前. 最后求所有点中,排名可以确定的点的个数. n <= 100, m <= 4500 刚开始还在想是不是拓扑 ...
- EXCEL常用命令
查找和选择:定位条件(定位空值.错误值) 选择性粘贴
- powerdesigner约束名唯一出错的解决办法
powerdesigner中自动生成的约束名有时会因为表的前缀一样而不具有唯一性,这样在生成时就会出错,一般的解决办法有以下两种: 1.模型=>Reference中可以看到当前模型中的所有Ref ...
- python + selenium + unittest 自动化测试框架 -- 入门篇
. 预置条件: 1. python已安装 2. pycharm已安装 3. selenium已安装 4. chrome.driver 驱动已下载 二.工程建立 1. New Project:建立自己的 ...
- 正则表达式 去除所有非ASCII字符
需求: 去除字符串中包含的所有外国字符 只能使用正则如下,找到包含非ASCII的记录 db=# select * from test where info ~ '[^(\x00-\x7f)]'; id ...
- Leetcode 436.寻找右区间
寻找右区间 给定一组区间,对于每一个区间 i,检查是否存在一个区间 j,它的起始点大于或等于区间 i 的终点,这可以称为 j 在 i 的"右侧". 对于任何区间,你需要存储的满足条 ...
- [java开发篇][dom模块] 遍历解析xml
http://blog.csdn.net/andie_guo/article/details/24844351 XML DOM节点树 XML DOM将XML文档作为树结构,树结构称为一个节点树.所有的 ...
- TOJ4537: n阶行列式
4537: n阶行列式 Time Limit(Common/Java):1000MS/3000MS Memory Limit:65536KByteTotal Submit: 28 ...
- redis安装、配置和启动
一.运行环境 1.vmware虚拟机上的centos7系统,安装步骤略,网上搜搜就有,连接工具:secureCRT 2.新安装的linux,是没有wget命令,所以先执行这个命令安装下:yum -y ...
- Linux Shell系列教程之(一)Shell简介
本文是Linux Shell系列教程的第(一)篇,更多shell教程请看:Linux Shell系列教程 想要学习linux,shell知识必不可少,今天就给大家来简单介绍下shell的基本知识. S ...