/*
一道有意思的查询题目, 属于交叉表的范围。
第一种写法用自联接求解,虽然写法比不上第二种高明,但当中有两个知识点值得习: Coalesce 与 FULL OUTER JOIN
在正式的场合,应当使用第2种比较高效的写法。
以下语句直接粘贴到查询分析器即可执行。
*/
SET NOCOUNT ON
GO
create table #t(NAME char(16),TYPE char(1),PUBDATE datetime)
insert into #t select 'A' ,'S','2005-4-1 00:00:00.000'
insert into #t select 'A' ,'S','2005-4-1 00:00:00.000'
insert into #t select 'A' ,'S','2005-4-3 00:00:00.000'
insert into #t select 'A' ,'S','2005-4-4 00:00:00.000'
insert into #t select 'B' ,'S','2005-4-4 00:00:00.000'
insert into #t select 'B' ,'S','2005-4-4 00:00:00.000'
insert into #t select 'A' ,'M','2005-4-1 00:00:00.000'
insert into #t select 'A','M','2005-4-2 00:00:00.000'
insert into #t select 'B' ,'M','2005-4-2 00:00:00.000'
insert into #t select 'B','M','2005-4-3 00:00:00.000'
-- 需要得出的数据如下:
-- PubDate M N Total
-- ---------- ----------- ----------- -----------
-- 2005-04-01 1 2 3
-- 2005-04-02 2 0 2
-- 2005-04-03 1 1 2
-- 2005-04-04 0 3 3
GO
---- 第一种写法 :
SELECT Convert(varchar(10),Coalesce(M.PubDate,N.PubDate),120) As PubDate
, Isnull(M.M,0) As M
, Isnull(N.S,0) AS S
, Isnull(M.M,0)+Isnull(N.S,0) As Total
FROM
(
Select PubDate, Case When Type = 'M' Then Cou end as M
FROM
(Select Pubdate , Type , Count(1) Cou From #t
Where Type = 'M' Group by Pubdate,Type ) A
) M
FULL OUTER JOIN
(
Select PubDate, Case When Type = 'S' Then Cou End as S
FROM
(Select Pubdate , Type , Count(1) Cou From #t
Where Type = 'S' Group by Pubdate,Type ) A
) N
ON M.PubDate = N.PubDate
GO
---- 第二种写法 :
select convert(char(10),PUBDATE,120) as PUBDATE
,count(case TYPE when 'M' then 'M' else null end) as [M]
,count(case TYPE when 'S' then 'S' else null end) as [S]
,count(*) as TOTAL from #t
group by convert(char(10),PUBDATE,120)
GO
drop table #t
SET NOCOUNT OFF