SQL 统计 字段 竖向转横向 (行转列)显示
Sql的行列(纵横表)转换
Sql的⾏列(纵横表)转换创建表scores⼀、传统的⾏列转换纵表转横表我们要转成的横表是这样⼦的:既然这个表只有两列,那么可以根据姓名进⾏分组。
先把姓名拼凑出来,后⾯的分数我们再想办法。
select姓名from scores group by 姓名结果:分析:1. 我们先拿到语⽂这个科⽬的分数。
既然我们⽤到了group by 语句,这⾥肯定要⽤聚合函数来求分数。
2. ⽽且我们只需要语⽂这⼀科的成绩,分组出来的⼀共有 3列,分别是语⽂、数学、物理。
那么就需要判断科⽬来取分数。
这⾥符合我们需求的 case 语句就登场了。
它和c#中switch-case 作⽤⼀样。
sql case 语句语法:case字段when 值1 then 结果when 值2 then 结果2...else默认结果endselect姓名,SUM(case课程 when '语⽂' then 分数else0 end) as语⽂from scores group by 姓名结果:既然语⽂的分数取到了,其他科⽬改变下条件就可以了。
完整的sql:select姓名,SUM(case课程 when '语⽂' then 分数else0 end) as语⽂,SUM(case课程 when '数学' then 分数else0 end) as数学,SUM(case课程 when '物理' then 分数else0 end) as物理from scores group by 姓名横表转纵表我们先把刚刚转好的表,插⼊⼀个新表Scores2中。
select姓名,SUM(case课程 when '语⽂' then 分数else0 end) as语⽂,SUM(case课程 when '数学' then 分数else0 end) as数学,SUM(case课程 when '物理' then 分数else0 end) as物理into scores2from scores group by 姓名我们也先把张三和李四的语⽂成绩查出来。
sql语句中行转列,以及列转行
sql语句中⾏转列,以及列转⾏⾏转列:图1: --------------------------------------------》》》》 图2:sql执⾏原理:根据id分组,然后select后⾯创建多次查询,⽣成列信息(利⽤case语句给分group by后的语句分类)-- ⾏转列select t.id,sum(case name when'仓库1'then t.num else NULL end) 仓库1,sum(case name when'仓库2'then t.num else NULL end) 仓库2,sum(case name when'仓库3'then t.num else NULL end) 仓库3from tGROUP BY t.id;列转⾏:图1: --------------------------------------------》》》》 图2:第⼀步:sql执⾏原理:每个select语句只查某⼀个字段的值,创建多个查询,然后将多个select语句通过union链接,实现⼀条多列数据变成多⾏⼀列;⽐如⼀⾏仓库1,仓库2,仓库3 最后变成多⾏select p.id, '仓库1' name, p.`仓库1` numfrom pr punionselect p.id, '仓库2' name, p.`仓库2` numfrom pr punionselect p.id, '仓库3' name, p.`仓库3` numfrom pr p执⾏结果:第⼆步:去掉为null的,即不存在⾏select*from (select p.id, '仓库1' name, p.`仓库1` num from pr punionselect p.id, '仓库2' name, p.`仓库2` num from pr punionselect p.id, '仓库3' name, p.`仓库3` num from pr p ) T where T.num is not null order by id, name。
纵表、横表互转的SQL
纵表、横表互转的SQL纵表、横表互转的SQLBy:⼤志若愚1、建表:纵表结构 Table_Acreate table Table_A(姓名varchar(20),课程varchar(20),成绩int)insert into Table_A(姓名,课程,成绩) values('张三','语⽂',60)insert into Table_A(姓名,课程,成绩) values('张三','数学',70)insert into Table_A(姓名,课程,成绩) values('张三','英语',80)insert into Table_A(姓名,课程,成绩) values('李四','语⽂',90)insert into Table_A(姓名,课程,成绩) values('李四','数学',100)姓名课程成绩张三语⽂60张三数学70张三英语80李四语⽂90李四数学100横表结构 Table_Bcreate table Table_B(姓名varchar(20),语⽂int,数学int,英语int)insert into Table_B(姓名,语⽂,数学,英语) values('张三',60,70,80)insert into Table_B(姓名,语⽂,数学,英语) values('李四',90,100,0)姓名语⽂数学英语张三607080李四9010002、纵表变横表纵表结构 Table_A --> 横表结构 Table_B⽅法⼀:聚合函数[max或sum]配合case语句select姓名,sum (case课程when'语⽂'then成绩else0end) as语⽂,sum (case课程when'数学'then成绩else0end) as数学,sum (case课程when'英语'then成绩else0end) as英语from Table_Agroup by姓名⽅法⼆:使⽤pivotselect*from Table_A pivot (max(成绩)for课程in(语⽂,数学,英语)) 临时表3、横表变纵表横表结构 Table_B --> 纵表结构 Table_A⽅法⼀:union allselect姓名,'语⽂'as课程,语⽂as成绩from Table_B union allselect姓名,'数学'as课程,数学as成绩from Table_B union allselect姓名,'英语'as课程,英语as成绩from Table_Border by姓名,课程desc⽅法⼆:使⽤unpivotselect姓名,课程,成绩from Table_Bunpivot(成绩for课程in ([语⽂],[数学],英语)) 临时表说明:在实际开发中表名,列名不应该使⽤汉字,在插⼊的值中有汉字的应该⽤N修饰,以防⽌出现乱码,出现意想不到的结果,可能产⽣2异性的表名可以⽤[]修饰。
SQL横排转竖排
sql查询竖排变横排及横排变竖排显示行列转换问题2013-06-27 11:01 4507人阅读评论(0) 收藏举报分类:SQL技术(5)假设有张学生成绩表(tb)如下:Name Subject Result张三语文74张三数学83张三物理93李四语文74李四数学84李四物理94-------------------------------------------------------------------------想变成姓名语文数学物理---------- ----------- ----------- -----------李四 74 84 94张三 74 83 93create table tb(Name varchar2(10) ,Subject varchar2(10) ,Result number);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)--静态SQL,指subject只有语文、数学、物理这三门课程。
sql的行转列(PIVOT)与列转行(UNPIVOT)
sql的⾏转列(PIVOT)与列转⾏(UNPIVOT)在做数据统计的时候,⾏转列,列转⾏是经常碰到的问题。
case when⽅式太⿇烦了,⽽且可扩展性不强,可以使⽤ PIVOT,UNPIVOT⽐较快速实现⾏转列,列转⾏,⽽且可扩展性强⼀、⾏转列1、测试数据准备CREATE TABLE[StudentScores]([UserName]NVARCHAR(20), --学⽣姓名[Subject]NVARCHAR(30), --科⽬[Score]FLOAT, --成绩)INSERT INTO[StudentScores]SELECT'张三', '语⽂', 80INSERT INTO[StudentScores]SELECT'张三', '数学', 90INSERT INTO[StudentScores]SELECT'张三', '英语', 70INSERT INTO[StudentScores]SELECT'张三', '⽣物', 85INSERT INTO[StudentScores]SELECT'李四', '语⽂', 80INSERT INTO[StudentScores]SELECT'李四', '数学', 92INSERT INTO[StudentScores]SELECT'李四', '英语', 76INSERT INTO[StudentScores]SELECT'李四', '⽣物', 88INSERT INTO[StudentScores]SELECT'码农', '语⽂', 60INSERT INTO[StudentScores]SELECT'码农', '数学', 82INSERT INTO[StudentScores]SELECT'码农', '英语', 96INSERT INTO[StudentScores]SELECT'码农', '⽣物', 782、⾏转列sqlSELECT*FROM[StudentScores]/*数据源*/AS PPIVOT(SUM(Score/*⾏转列后列的值*/) FORp.Subject/*需要⾏转列的列*/IN ([语⽂],[数学],[英语],[⽣物]/*列的值*/)) AS T执⾏结果:⼆、列转⾏1、测试数据准备CREATE TABLE ProgrectDetail(ProgrectName NVARCHAR(20), --⼯程名称OverseaSupply INT, --海外供应商供给数量NativeSupply INT, --国内供应商供给数量SouthSupply INT, --南⽅供应商供给数量NorthSupply INT--北⽅供应商供给数量)INSERT INTO ProgrectDetailSELECT'A', 100, 200, 50, 50UNION ALLSELECT'B', 200, 300, 150, 150UNION ALLSELECT'C', 159, 400, 20, 320UNION ALL2、列转⾏的sqlSELECT P.ProgrectName,P.Supplier,P.SupplyNumFROM(SELECT ProgrectName, OverseaSupply, NativeSupply,SouthSupply, NorthSupplyFROM ProgrectDetail)TUNPIVOT(SupplyNum FOR Supplier IN(OverseaSupply, NativeSupply, SouthSupply, NorthSupply ) ) P执⾏结果:。
sql查询中的纵向连接和横向连接
sql查询中的纵向连接和横向连接sql 查询中的纵向连接和横向连接:
纵向连接都是采⽤ left join , right join ,inner join:
左连接,右连接,内连接,都是对两个表的字段根据条件,进⾏横向拼接
横向连接都是采⽤ union all :
是对查询出来的结果集进⾏合并,要求两个表的列名和类型都⼀致
SELECT column_name(s) FROM table_name1
UNION ALL
SELECT column_name(s) FROM table_name2
union的特性,去重与不去重
集合操作有 并,交,差 3种运算:
union: 得到两个查询结果的并集,并且⾃动去掉重复⾏。
不会排序
union all: 得到两个查询结果的并集,不会去掉重复⾏。
也不会排序
intersect: 得到两个查询结果的交集,并且按照结果集的第⼀个列进⾏排序
minus: 得到两个查询结果的减集,以第⼀列进⾏排序。
SQL竖表转换成横表统计
SQL竖表转换成横表统计#创建表user_scorecreate table user_score(name varchar(20),subjects varchar(20),score int);insert into user_score(name,subjects,score) values('张三','语⽂',60);insert into user_score(name,subjects,score) values('张三','数学',70);insert into user_score(name,subjects,score) values('张三','英语',80);insert into user_score(name,subjects,score) values('李四','语⽂',90);insert into user_score(name,subjects,score) values('李四','数学',100);#创建表user_score2create table user_score2(name varchar(20),yuwen int,shuxue int,yingyu int);insert into user_score2(name,yuwen,shuxue,yingyu) values('张三',60,70,80);insert into user_score2(name,yuwen,shuxue,yingyu) values('李四',90,100,0);#纵表转横表select name,sum(case subjects when '语⽂' then score else 0 end) as '语⽂',sum(case subjects when '数学' then score else 0 end) as '数学',sum(case subjects when '英语' then score else 0 end) as '英语'from user_score group by name;#纵表转横表SELECT name, 'yuwen' AS subjects, yuwen AS score FROM user_score2 UNION ALLSELECT name, 'shuxue' AS subjects, shuxue AS score FROM user_score2 UNION ALLSELECT name, 'yingyu' AS subjects, yingyu AS score FROM user_score2ORDER BY name,subjects DESC;。
SQLServer数据库纵向转横向
22 IN ([/101],[/103],[/401],[/402])) AS PivotTable
结果为: 以上为记录笔记,无他用。
1 SELECT 2 ssp_pay_empid, 3 ssp_pay_sdate, 4 ssp_pay_edate, 5 ssp_pay_type, 6 ssp_pay_amount, 7 ssp_pay_item 8 FROM ssp_pay 9 where ssp_pay_empid = 00000073 and ssp_pay_type = 'RT' and ssp_pay_item 10 IN ('/101','/103','/401','/402') and ssp_pay_sdate = '2007-08-01'
4 ssp_pay_edate,
5 ssp_pay_type,
6 [/101],
7 [/103],
8 [/401],
9 [/402]
10 from (
11 SELECT
12
ssp_pay_empid,
13
ssp_pay_sdate,
14
ssp_pay_edate,
15
ssp_pay_type,
16
ssp_pay_amount,
需要将上述查询结果显示为一行则使用sqlserver2005新增的pivot通过将表达式某一列中的唯一值转换为输出中的多个列来旋转表值表达式并在必要时对最终输出中所需的任何其余列值执行聚合
SQLServer数 据 库 纵 向 转 横 向
以一张薪资表为例,表结构如下:
表结构中,每个员工id对应有多个薪资项目以及金额,需要查询时转向,将每个员工的薪资项目转为横向一行显示。 在直接查询(加入一些限制条件以缩小结果集),
SQL竖列变横列
oracle中自连接和case when,decode的应用有表如下:* from test026;ID NAME SUBJECT SCORE---------- -------------------- -------------------- ----------1 jim 语文 881 jim 数学 841 jim 英语 902 kate 语文 862 kate 数学 762 kate 英语 96想得到如下效果:学生编号学生姓名语文数学英语方法:1.自连接:(这是自连接很典型的用处应当熟练掌握)select a.id,,a.score as "语文",b.score as "数学",c.score as "英语"2 from test026 a,test026 b,test026 c3 where a.id=b.id and a.subject='语文' and b.subject='数学'4 and a.id=c.id and c.subject='英语';ID NAME 语文数学英语---------- -------------------- ---------- ---------- ----------1 jim 88 84 902 kate 86 76 962 使用case when(数值)Select id,name,2 sum(case when subject='语文' then score end) as "语文",3 sum(case when subject='数学' then score end) as "数学",4 sum(case when subject='英语' then score end) as "英语"5 from test0266 group by id,name7 /ID NAME 语文数学英语---------- -------------------- ---------- ---------- ----------1 jim 88 84 902 kate 86 76 963 oracle独用decode1 select max(id) as id,name,2 max(decode(subject,'数学',score)) as "数学",3 max(decode(subject,'语文',score)) as "语文",4 max(decode(subject,'英语',score)) as "英语"5 from test0266* group by nameID NAME 数学语文英语---------- -------------------- ---------- ---------- ----------1 jim 84 88 902 kate 76 86 96。
在sql语句中怎样将数据库字段横着显示出来
在sql语句中怎样将数据库字段横着显⽰出来交叉数据报表有时候需要旋转结果以便在⽔平⽅向显⽰列,⽽在垂直⽅向显⽰⾏。
这就是所谓的创建 PivotTable®、创建交叉数据报表或旋转数据。
假定有⼀个表 Pivot,其中每季度占⼀⾏。
对 Pivot 的 SELECT 操作在垂直⽅向上列出这些季度:Year Quarter Amount---- ------- ------1990 1 1.11990 2 1.21990 3 1.31990 4 1.41991 1 2.11991 2 2.21991 3 2.31991 4 2.4⽣成报表的表必须是这样的,其中每年占⼀⾏,每个季度的数值显⽰在⼀个单独的列中,如:YearQ1Q2Q3Q419901.11.21.31.419912.12.22.32.4下⾯的语句⽤于创建 Pivot 表并在其中填⼊第⼀个表中的数据:USE NorthwindGOCREATE TABLE Pivot( Year SMALLINT,Quarter TINYINT,Amount DECIMAL(2,1) )GOINSERT INTO Pivot VALUES (1990, 1, 1.1)INSERT INTO Pivot VALUES (1990, 2, 1.2)INSERT INTO Pivot VALUES (1990, 3, 1.3)INSERT INTO Pivot VALUES (1990, 4, 1.4)INSERT INTO Pivot VALUES (1991, 1, 2.1)INSERT INTO Pivot VALUES (1991, 2, 2.2)INSERT INTO Pivot VALUES (1991, 3, 2.3)INSERT INTO Pivot VALUES (1991, 4, 2.4)GO下⾯是⽤于创建旋转结果的 SELECT 语句:SELECT Year,SUM(CASE Quarter WHEN 1 THEN Amount ELSE 0 END) AS Q1,SUM(CASE Quarter WHEN 2 THEN Amount ELSE 0 END) AS Q2,SUM(CASE Quarter WHEN 3 THEN Amount ELSE 0 END) AS Q3,SUM(CASE Quarter WHEN 4 THEN Amount ELSE 0 END) AS Q4FROM Northwind.dbo.PivotGROUP BY YearGO该 SELECT 语句还处理其中每个季度占多⾏的表。
SQL纵表横表互转
SQL纵表横表互转纵表、横表纵表:student1图1横表:student2图2方法一:1)纵表转横表(CASE):SELECT s_no,s_name,s_sex,SUM(CASE s_type WHEN'身高'THEN s_value ELSE 0 END)AS s_height, SUM(CASE s_type WHEN'体重'THEN s_value ELSE 0 END)AS s_weight FROM student1GROUP BY s_no,s_name,s_sex执行该查询后可以得到横表结构student2。
注释:图3通过CASE查询得到图3结果,再利用GROUP BY的分组功能,再加上别名,就得到完整的转换语句。
2)横表转纵表:SELECT s_no,s_name,s_sex,'身高'AS s_type,s_height AS s_value FROM student2UNION ALLSELECT s_no,s_name,s_sex,'体重'AS s_type,s_weight AS s_value FROM student2ORDER BY s_no,s_type注:方法一是利用最基本的查询语句来完成纵表横互转功能,可以看出随着列的增加代码量也会增加。
方法二:1)纵表转横表(PIVOT):SELECT s_no,s_name,s_sex,--基础列身高AS s_height,--透视列与IN里面对应体重AS s_weightFROM student1--纵表(源表,也可以是一个select查询结果)PIVOT(SUM(s_value)--透视列对应值所在的列FOR s_type--需要转换为行的列IN(身高,体重)--IN里面是透视列)AS PivotTable--透视表注释:使用POVIT首先你需要在FROM子句内定义2个表:一个称为源表(student1)。
最全的竖转横的SQL解释方法
最全的竖转横的SQL解释⽅法普通⾏列转换问题:假设有张学⽣成绩表(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 tbgroup by 姓名--SQL SERVER 2000 动态SQL,指课程不⽌语⽂、数学、物理这三门课程。
SQL SERVER数据库纵表转横表应用浅析
SQL SERVER数据库纵表转横表应用浅析在管理系统开发中,经常遇到纵表转横表或者横表转纵表的需求,由于发现各语法都能达到需求,或者有些语法在字段不是很多的时候能达到,但是运行效率相差很多,下面将遇到的各种语法进行总结,希望对同行在有需要的情况下能有所帮助。
标签:数据库sql server 纵表转横表0 引言模型描述:将下图所示的纵表(表1)的数据转为横表(表2),在同一报表中同时显示每个人员的不同月份的销售金额,年度暂定为2009年。
具体实现:在系统中,有三个表,字段信息如下表1:人员、回款、回款日期;经过分析sql server的应用总结以及对sqlserver帮助潜心专研,感触颇深,现总结如下与各位朋友共同分享,如有更好或者更方便的建议,请赐教,在此先谢过。
本方法适用SQLserver2000及以上。
为了直观些,表名与字段名称等信息一律使用汉字名称。
建表语句如下所示:CREATE TABLE [dbo].[表1] ([ID] [int] IDENTITY (1, 1) NOT NULL ,[人员] [varchar] (50) COLLATE Chinese_PRC_CI_AS NULL[合同金额] [decimal](18, 0) NULL ,[合同日期] [datetime] NULL) ON [PRIMARY]建立一个视图,如下语句所示:CREATE VIEW dbo.VIEW1 ASSELECT 人员, 销售金额, YEAR(销售日期) AS 年度, MONTH(销售日期) AS 月份FROM dbo.表1利用下面的语句插入数据insert into dbo.表1 (人员,销售金额,销售日期)select ‘张三’ ,12,’2009-01-01’ union allselect ‘张三’ ,86,’2009-07-09’ union allselect ‘张三’ ,89,’2009-08-21’ union allselect ‘张三’ ,88,’2009-12-31’ union allselect ‘李四’ ,99,’2009-02-21’ union allselect ‘李四’ ,36,’2009-03-01’ union allselect ‘李四’ ,68,’2009-06-11’ union allselect ‘李四’ ,88,’2009-09-21’ union allselect ‘王五’ ,89,’2009-03-31’ union allselect ‘王五’ ,99,’2009-10-31’ union allselect ‘赵六’ ,78,’2009-05-31’ union allselect ‘赵六’ ,65,’2009-11-21’通过下面的视图将各月份的销售金额进行汇总:CREATE VIEW dbo.VIEW2AS SELECT 人员, 月份, SUM(销售金额) AS销售金额FROM dbo.VIEW1 GROUP BY 人员, 年度, 月份经过以上准备,各项基本信息齐备,下面将通过VIEW2视图得到的数据分别说明纵表转横表sql语句1 通过求最大值的方法,此法效率相对较低SELECT 人员, MAX(a) AS ‘1’,MAX(b) AS ‘2’, MAX(c) AS ‘3’, MAX(d) AS ‘4’, MAX(e) AS ‘5’, MAX(f) AS ‘6’, MAX(g)AS ‘7’, MAX(h) AS ‘8’, MAX(i) AS ‘9’, MAX(j) AS ‘10’, MAX(k) AS ‘11’, MAX(l) AS ‘12’ FROM(SELECT 人员, CASE 月份WHEN 1 THEN 销售金额END AS ‘a’,CASE 月份WHEN 2 THEN 销售金额END AS ‘b’,CASE 月份WHEN 3 THEN 销售金额END AS ‘c’,CASE 月份WHEN 4 THEN 销售金额END AS ‘d’,CASE 月份WHEN 5 THEN 销售金额END AS ‘e’,CASE 月份WHEN 6 THEN 銷售金额END AS ‘f’,CASE 月份WHEN 7 THEN 销售金额END AS ‘g’,CASE 月份WHEN 8 THEN 销售金额END AS ‘h’,CASE 月份WHEN 9 THEN 销售金额END AS ‘i’,CASE 月份WHEN 10 THEN 销售金额END AS ‘j’,CASE 月份WHEN 11 THEN 销售金额E ND AS ‘k’,CASE 月份WHEN 12 THEN 销售金额END AS ‘l’FROM view2) AS a GROUP BY 人员order by 人员结果如下:2 表链接法,此法效率极低,但是也可以得到同样结果select distinct(view2.人员),tt1.销售金额‘1’ ,tt2.销售金额‘2’ ,tt3.销售金额‘3’,tt4.销售金额‘4’,tt5.销售金额‘5’,tt6.销售金额‘6’,tt7.销售金额‘7’,tt8.销售金额‘8’,tt9.销售金额‘9’,tt10.销售金额‘10’,tt11.销售金额‘11’,tt12.销售金额‘12’ from view2left join (select 人员,销售金额from view2 where 月份= 1) tt1 on tt1.人员=view2.人员left join (select 人员,销售金额from view2 where 月份= 2) tt2 on tt2.人员=view2.人员……left join (select 人员,销售金额from view2 where 月份= 12) tt12 on tt12.人员=view2.人员结果如1所示。
sql分组统计查询并横纵坐标转换
sql分组统计查询并横纵坐标转换关于sql 分组统计查询,我们在做报表的时候经常需要⽤到;今天就在这⾥整理下;先附上⼀段sql代码:if object_id(N'#mytb',N'U') is not null drop table #mytbgodeclare @Year intset @Year=2014create table #mytb ([Date] int,[Count] int,[Price] decimal(18, 0),[spbm] varchar(50),[sppp] varchar(100),[spmc] varchar(500))insert #mytbselect *from(selectm as [Date],sum(case when datepart(month,c.addtime)=mthen ordernum else 0 end) as [Count] ,sum(case when datepart(month,c.addtime)=mthen ordernum*orderPrice else 0 end) as Price,c.spbm,s.sppp,s.spmcfromTB_CusorderDetail c left join TB_SPXX s on c.spbm=s.spbm,(select 1 munion all select 2union all select 3union all select 4union all select 5union all select 6union all select 7union all select 8union all select 9union all select 10union all select 11union all select 12) aawhere@Year=year(c.addtime)and c.delstatus=0 and c.spbm in (SELECT spbm FROM TB_SPXX WHERE delstatus=0 AND isupinfo=1 AND spbm LIKE '1%' AND LEN(SPBM)>7)group bym,c.spbm,s.sppp,s.spmc)zselect sppp,spmc,spbm,max(case [Date] when 1 then [Count] else 0 end) '⼀⽉份总量',max(case [Date] when 1 then [Price] else 0 end) '⼀⽉份总额',max(case [Date] when 2 then [Count] else 0 end) '⼆⽉份总量',max(case [Date] when 2 then [Price] else 0 end) '⼆⽉份总额',max(case [Date] when 3 then [Count] else 0 end) '三⽉份总量',max(case [Date] when 3 then [Price] else 0 end) '三⽉份总额',max(case [Date] when 4 then [Count] else 0 end) '四⽉份总量',max(case [Date] when 4 then [Price] else 0 end) '四⽉份总额',max(case [Date] when 5 then [Count] else 0 end) '五⽉份总量',max(case [Date] when 5 then [Price] else 0 end) '五⽉份总额',max(case [Date] when 6 then [Count] else 0 end) '六⽉份总量',max(case [Date] when 6 then [Price] else 0 end) '六⽉份总额',max(case [Date] when 7 then [Count] else 0 end) '七⽉份总量',max(case [Date] when 7 then [Price] else 0 end) '七⽉份总额',from #mytbgroup by sppp,spmc,spbm关于这段sql代码,剖析如下:1:新建⼀个临时表#mytbcreate table #mytb ([Date] int,[Count] int,[Price] decimal(18, 0),[spbm] varchar(50),[sppp] varchar(100),[spmc] varchar(500))2:分组查询12个⽉份数据select *from(selectm as [Date],sum(case when datepart(month,c.addtime)=mthen ordernum else 0 end) as [Count] ,sum(case when datepart(month,c.addtime)=mthen ordernum*orderPrice else 0 end) as Price,c.spbm,s.sppp,s.spmcfromTB_CusorderDetail c left join TB_SPXX s on c.spbm=s.spbm,(select 1 munion all select 2union all select 3union all select 4union all select 5union all select 6union all select 7union all select 8union all select 9union all select 10union all select 11union all select 12) aawhere@Year=year(c.addtime)and c.delstatus=0 and c.spbm in (SELECT spbm FROM TB_SPXX WHERE delstatus=0 AND isupinfo=1 AND spbm LIKE '1%' AND LEN(SPBM)>7)group bym,c.spbm,s.sppp,s.spmc)z这段sql主要根据年份查询当年12个⽉份售出的产品统计;3:横纵坐标转换把分组查询出来的数据插⼊到临时表中后select sppp,spmc,spbm,max(case [Date] when 1 then [Count] else 0 end) '⼀⽉份总量',max(case [Date] when 1 then [Price] else 0 end) '⼀⽉份总额',max(case [Date] when 2 then [Count] else 0 end) '⼆⽉份总量',max(case [Date] when 2 then [Price] else 0 end) '⼆⽉份总额',max(case [Date] when 3 then [Count] else 0 end) '三⽉份总量',max(case [Date] when 3 then [Price] else 0 end) '三⽉份总额',max(case [Date] when 4 then [Count] else 0 end) '四⽉份总量',max(case [Date] when 4 then [Price] else 0 end) '四⽉份总额',max(case [Date] when 6 then [Count] else 0 end) '六⽉份总量', max(case [Date] when 6 then [Price] else 0 end) '六⽉份总额', max(case [Date] when 7 then [Count] else 0 end) '七⽉份总量', max(case [Date] when 7 then [Price] else 0 end) '七⽉份总额', max(case [Date] when 8 then [Count] else 0 end) '⼋⽉份总量', max(case [Date] when 8 then [Price] else 0 end) '⼋⽉份总额' from #mytbgroup by sppp,spmc,spbm;利⽤⽇期昨晚扭转横纵坐标;最后附上⼀图,体现最终结果。
MSSQLServer纵向表转横向表横向表转纵向表行转列列转行
MSSQLServer纵向表转横向表横向表转纵向表⾏转列列转⾏MSSQLServer 纵向表转横向表横向表转纵向表建表语句及插⼊数据语句:CREATE TABLE Test_y([Name][nchar](10) NULL,[Course][nchar](10) NULL,[Grade][int]NULL)insert into Test_y values ('张三','语⽂',75);insert into Test_y values ('张三','数学',80);insert into Test_y values ('张三','英语',90);insert into Test_y values ('李四','语⽂',90);insert into Test_y values ('李四','数学',70);insert into Test_y values ('李四','英语',80);CREATE TABLE Test_x([Name][nchar](10) NULL,[语⽂][nchar](10) NULL,[数学][nchar](10) NULL,[英语][nchar](10) NULL)insert into Test_x values('张三',75,80,90);insert into Test_x values('李四',90,70,80);纵向表转横向表效果展⽰:纵向表转横向表 sql 语句如下:⽅法⼀:select*from Test_y;select Name,sum(case Course when'语⽂'then Grade else0end) as语⽂,sum(case Course when'数学'then Grade else0end) as数学,sum(case Course when'英语'then Grade else0end) as英语from Test_y group by Name;⽅法⼆:select * From Test_ypivot(sum(Grade) for Course IN ([语⽂],[数学],[英语]))AS Test_x;横向表转纵向表效果展⽰:横向表转纵向表 sql 语句如下:⽅法⼀:select*from Test_x;select Name,'语⽂'as Course,语⽂as Gradefrom Test_x union allselect Name,'数学'as Course,数学as Gradefrom Test_x union allselect Name,'英语'as Course,英语as Gradefrom Test_x order by Name desc;⽅法⼆:select Name,Course,Grade from Test_xunpivot(Grade for Course in([数学],[英语],[语⽂]))as Test_y最后谢谢 @漠北⽔獭的提⽰。
myql数据库,sql横排转竖排以及竖排转横排,oracle的over函数的使用
myql数据库,sql横排转竖排以及竖排转横排,oracle的over函数的使⽤⼀、引⾔ 前些⽇⼦遇到了⼀个sql语句的横排转竖排以及竖排转横排的问题,现在该总结⼀下,具体问题如下:这⾥的第⼆题和第三题和下⾯所讲述的学⽣的成绩表是相同的,这⾥给⼤家留⼀下⼀个念想,⼤家可以⾃⼰做做上⾯的笔试题。
我主要针对的是第⼆题和第三题来做讲解,第⼀题相信⼤家都会做,这⾥就不赘述了,直接进⼊正题!⼆、问题详解 1、我们先来说说第⼆题, (1)⾸先我们先创建⼀个表,⽤实际来说话,新建⼀个tb表,DROP TABLE tb;CREATE TABLE tb(name varchar(10),subject VARCHAR(10),score NUMERIC);INSERT INTO tb(name,SUBJECT,score) VALUES('张三','语⽂',74);INSERT INTO tb(name,SUBJECT,score) VALUES('张三','数学',83);insert into tb(Name , Subject , score) values('张三' ,'物理' , 93);insert into tb(Name , Subject , score) values('李四' , '语⽂' , 74);insert into tb(Name , Subject , score) values('李四' , '数学' , 84);insert into tb(Name , Subject , score) values('李四' , '物理' , 94);SELECT*FROM tb;(2)最初的查询结果如图所⽰(3)下⾯我们开始竖排转横排SELECT NAME 姓名,MAX(CASE SUBJECT WHEN'语⽂'THEN score ELSE0END) 语⽂,MAX(CASE SUBJECT WHEN'数学'THEN score ELSE0END) 数学,MAX(CASE SUBJECT WHEN'物理'THEN score ELSE0END) 物理FROM tb GROUP BY NAME结果是:(4)进⼀步的拓展,假如我们想要的结果为下图SELECT NAME 姓名,MAX(CASE SUBJECT WHEN'语⽂'THEN score ELSE0END) 语⽂,MAX(CASE SUBJECT WHEN'数学'THEN score ELSE0END) 数学,MAX(CASE SUBJECT WHEN'物理'THEN score ELSE0END) 物理,SUM(score) AS总分,AVG(score) AS平均分FROM tb GROUP BY NAME2、下⾯来讨论⼀下横排转竖排的问题(1)⾸先创建表tb1,CREATE TABLE tb1(姓名VARCHAR(10),语⽂ NUMERIC,数学 NUMERIC,物理 NUMERIC);insert into tb1(姓名 , 语⽂ , 数学 , 物理) values('张三',74,83,93);insert into tb1(姓名 , 语⽂ , 数学 , 物理) values('李四',74,84,94);SELECT*FROM tb1;如图所⽰:(2)横排转竖排⽅法⼀:select姓名as name,'语⽂'as subject,语⽂as score from tb1unionselect姓名as name,'数学'as subject,数学as score from tb1unionselect姓名as name,'物理'as subject,物理as score from tb1order by name⽅法⼆:SELECT*FROM (SELECT姓名as NAME,'语⽂'AS SUBJECT, 语⽂AS score from tb1 UNION SELECT姓名AS NAME,'数学'AS SUBJECT , 数学AS score from tb1 UNION SELECT姓名AS NAME,'物理'AS SUBJECT, 物理AS score FROM tb1)t ORDER BY NAME结果为:3、下⾯讨论⼀下第三题(1)创建表tb2CREATE TABLE tb2(YEAR NUMBER,salary NUMBER);INSERT INTO tb2(YEAR,salary) VALUES(2000,1000);INSERT INTO tb2(YEAR,salary) VALUES(2001,2000);INSERT INTO tb2(YEAR,salary) VALUES(2002,3000);INSERT INTO tb2(YEAR,salary) VALUES(2003,4000);SELECT*FROM tb2;如图:(2)利⽤over函数完成所需要求,select year,sum(salary) over(order by salary) from tb2考察开窗函数的,。
Sql纵向表转为横向表,并分组统计。
Sql纵向表转为横向表,并分组统计。
在写系统尤其是在写课程系统是经常会遇到类似如下纵-横转换,在使⽤group by ... with cube/rollup + grouping() 来实现是⾮常容易做到的。
1. ⽤于测试的数据如下:declare@tab table(Class varchar(20),Student varchar(20),Course varchar(50),Grades decimal(7,2));insert into@tab(Class,Student,Course,Grades) values('A班','张三','语⽂',60);insert into@tab(Class,Student,Course,Grades) values('A班','张三','数学',70);insert into@tab(Class,Student,Course,Grades) values('A班','张三','英语',80);insert into@tab(Class,Student,Course,Grades) values('A班','李四','语⽂',30);insert into@tab(Class,Student,Course,Grades) values('A班','李四','数学',40);insert into@tab(Class,Student,Course,Grades) values('A班','李四','英语',50);insert into@tab(Class,Student,Course,Grades) values('B班','王五','语⽂',65);insert into@tab(Class,Student,Course,Grades) values('B班','王五','数学',75);insert into@tab(Class,Student,Course,Grades) values('B班','王五','英语',85);insert into@tab(Class,Student,Course,Grades) values('B班','赵六','语⽂',35);insert into@tab(Class,Student,Course,Grades) values('B班','赵六','数学',45);insert into@tab(Class,Student,Course,Grades) values('B班','赵六','英语',55);select*from@tab2. 实现此效果的SQL语句如下:select(case when Grouping(Class)=1then'总平均'when Grouping(Student)=1then''else Class end ) as Class,(case when Grouping(Class)=1then''when Grouping(Student)=1then'平均'else Student end) as Student,cast(avg(语⽂) as decimal(7,2)) as语⽂,cast(avg(数学) as decimal(7,2)) as数学,cast(avg(英语) as decimal(7,2)) as英语,cast(avg(总分) as decimal(7,2)) as总分from (select Class,Student,(select isnull(sum(Grades),0) from@tab where Class=t.Class and Student=t.Student and Course='语⽂') as'语⽂',(select isnull(sum(Grades),0) from@tab where Class=t.Class and Student=t.Student and Course='数学') as'数学',(select isnull(sum(Grades),0) from@tab where Class=t.Class and Student=t.Student and Course='英语') as'英语',(select isnull(sum(Grades),0) from@tab where Class=t.Class and Student=t.Student) as'总分'from@tab as tgroup by Class,Student) as tempTabgroup by Class,Student,语⽂,数学,英语,总分with rolluphaving Grouping(语⽂)=1and Grouping(数学)=1and Grouping(英语)=1这⾥没有考虑做到通⽤,如果做到通⽤可能会⽐较复杂,也不知道性能会怎么样。
sql如何将纵向数据列表转化为横向数据字段
sql如何将纵向数据列表转化为横向数据字段sql怎么将纵向数据列表转化为横向数据字段如题,求高手!------解决方案--------------------/u/20080614/17/22e73f33-f071-46dc-b9bf-321204b1656f.html?33238------解决方案--------------------SQL code昨天猜测了今天再猜估计是90度旋转--------------------------------------/*数据库中tb表格如下月份工资福利奖金1月 100 200 3002月 110 210 3103月 120 220 3204月 130 230 330我想得到的结果是项目 1月 2月 3月 4月工资 100 110 120 130福利 200 210 220 230奖金 300 310 320 330就是说完全把表格的行列颠倒,有点像那种旋转矩阵,请问如何用sql 语句实现?*/if exists (select * from dbo.sysobjectswhere id = object_id(N'[dbo].[p_zj]') and OBJECTPROPERTY(id, N'IsProcedure') = 1)drop procedure [dbo].[p_zj]GO/*--行列互换的通用存储过程(原著:邹建):将指定的表,按指定的字段进行行列互换*/create proc p_zj@tbname sysname, --要处理的表名@fdname sysname, --做为转换的列名@new_fdname sysname='' --为转换后的列指定列名asdeclare @s1 varchar(8000) , @s2 varchar(8000),@s3 varchar(8000) , @s4 varchar(8000),@s5 varchar(8000) , @i varchar(10)select @s1 = '' , @s2 = '' , @s3 = '' , @s4 = '' , @s5 = '' , @i = '0'select @s1 = @s1 + ',@' + @i + ' varchar(8000)',@s2 = @s2 + ',@' + @i + '=''' + case isnull(@new_fdname , '') when '' then ''else @new_fdname + '=' end + '''''' + name + '''''''',@s3 = @s3 + 'select @' + @i + '=@' + @i + '+'',['' + [' + @fdname +']+'']=''+cast([' + name + '] as varchar) from [' + @tbname + ']',@s4 = @s4 + ',@' + @i + '=''select ''+@' + @i,@s5 = @s5 + '+'' union all ''+@' + @i,@i=cast(@i as int)+1from syscolumnswhere object_id(@tbname)=id and name<>@fdnameselect @s1=substring(@s1,2,8000),@s2=substring(@s2,2,8000),@s4=substring(@s4,2,8000),@s5=substring(@s5,16,8000)exec('declare ' + @s1 + 'select ' + @s2 + @s3 + 'select ' + @s4 + 'exec(' + @s5 + ')')go--用上面的存储过程测试:create table Test(月份 varchar(4), 工资 int, 福利 int, 奖金 int) insert Testselect '1月',100,200,300 union allselect '2月',110,210,310 union allselect '3月',120,220,320 union allselect '4月',130,230,330goexec p_zj 'Test', '月份' , '项目'drop table Testdrop proc p_zj/*项目 1月 2月 3月 4月---- ----------- ----------- ----------- -----------福利 200 210 220 230工资 100 110 120 130奖金 300 310 320 330(所影响的行数为 3 行)*//*静态写法(SQL2005)*/--测试环境create table Test(月份 varchar(4), 工资 int, 福利 int, 奖金 int) insert Testselect '1月',100,200,300 union allselect '2月',110,210,310 union allselect '3月',120,220,320 union allselect '4月',130,230,330go--测试语句SELECT * FROM(SELECT 考核月份,月份,金额 FROM(SELECT 月份, 工资, 福利, 奖金 FROM T est) pUNPIVOT(金额 FOR 考核月份 IN (工资, 福利, 奖金))AS unpvt) TPIVOT(MAX(金额) FOR 月份 in ([1月],[2月],[3月],[4月]))AS pt--测试结果/*考核月份 1月 2月 3月 4月------- ----- ----- ------ -------福利200210220230工资100110120130奖金300310320330*/--删除环境Drop table Test------解决方案--------------------SQL code/*标题:普通行列转换(version 2.0)作者:爱新觉罗.毓华(十八年风雨,守得冰山雪莲花开)时间:2008-03-09地点:广东深圳说明:普通行列转换(version 1.0)仅针对sql server 2000提供静态和动态写法,version 2.0增加sql server 2005的有关写法。
(转载)SQL语句,纵列转横列
货物编号 库位1 库位2 库位3 0101 50 90 120 0102 60 110 0103 50 100 0111 30 请问用一句sql语句怎么实现?
select a.货物编号,sum(b.库存数),sum(c.库存数),sum(d.库存数) from stable a left join (select 货物编号, 库存数 from stable where 库位=1)b on a.货物编号=b.货物编号 left join (select 货物编号, 库存数 from stable where 库位=2)c on a.货物编号=c.货物编号 left join (select 货物编号, 库存数 from stable where 库位=3)c on a.货物编号=d.货物编号 group by a.货物编号
网络错误503请刷新页面重试持续报错请尝试更换浏览器或网络环境
SQL语句,纵列转横列
(转载) SQL语句,纵列转横列
Fhor: wzmbox Comments
sTable.db 库位 货物编号 库存数 1 0101 50 1 0102 60 1 0103 50 2 0101 90 2 0103 100 2 0111 30 3 0101 120 3 0102 110 4 0101 11
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
在做一些SQL统计时,为了更直观看到结果,并进行比较,需要把竖向表的部分统计字段转成横向显示。
原数据格式:
wbname news time
------------------------------
潇湘晨报直播报道
佛山日报后天
扬子晚报昨天
扬子晚报昨天
足球报直播报道
足球报直播报道
中山日报昨天
要统计成横向结构
wbname 昨天直播报道后天
------------------------------------------------------
潇湘晨报0 1 0
佛山日报 0 0 1
扬子晚报 2 0 0
足球报 0 2 0
中山日报 1 0 0
数据库表的结构
Field Type
-------- -----------
id int(11)
wbname varchar(50)
newstime varchar(50)
测试数据(MySQL)
insert into `wb`(`id`,`wbname`,`newstime`) values
(1,'潇湘晨报','直播报道'),
(2,'佛山日报','后天'),
(3,'扬子晚报','昨天'),
(4,'扬子晚报','昨天'),
(5,'足球报','直播报道'),
(6,'足球报','直播报道'),
(7,'中山日报','昨天'),
(8,'中山日报','当天'),
(9,'中山日报','直播报道'),
(10,'钱江晚报','直播报道'),
(11,'南方日报','时间不详'),
(12,'广州日报','直播报道'),
(13,'中国经营报','时间不详'), (14,'中国经营报','时间不详'), (15,'中国经营报','上周'),
(16,'烟台日报传媒集团','时间不详'), (17,'烟台日报传媒集团','其他'), (18,'烟台日报传媒集团','上周'), (19,'扬子晚报','时间不详'),
(20,'扬子晚报','上周'),
(21,'扬子晚报','时间不详'),
(22,'扬子晚报','时间不详'),
(23,'扬子晚报','当天'),
(24,'扬子晚报','时间不详'),
(25,'潇湘晨报','时间不详'),
(26,'足球报','直播报道'),
(27,'足球报','直播报道'),
(28,'潇湘晨报','其他'),
(29,'潇湘晨报','其他'),
(30,'足球报','直播报道'),
(31,'足球报','直播报道'),
(32,'足球报','直播报道'),
(33,'足球报','直播报道'),
(34,'足球报','直播报道'),
(35,'足球报','直播报道'),
(36,'潇湘晨报','当天'),
(37,'足球报','直播报道'),
(38,'潇湘晨报','直播报道'),
(39,'潇湘晨报','直播报道'),
(40,'潇湘晨报','直播报道'),
(41,'潇湘晨报','直播报道');
主角:SQL语句
select wbname
,su m(case when newstime='上周' then total e ls e 0 end) as '上周'
,sum(case when newstime='昨天' then total else 0 end) as '昨天'
,sum(case when newstime='当天' then total else 0 end) as '当天'
,sum(case when newstime='直播报道' then total else 0 end) as '直播报道'
,sum(case when newstime='时间不详' then total else 0 end) as '时间不详'
,sum(case when newstime='其他' then total else 0 end) as '其他'
from (
select wbname,newstime,count(*) as total from wb group by wbname,newstime
as temp group by wbname;。