我在创建一个使用一些二进制文件或范围的SQL查询时遇到了问题。
我有一张桌子,看起来像这样:
Id Value Range
1 101 >100
2 8 >5
3 330 >100
4 230 >100
5 8 >5
6 101 >100
7 8 >5
8 330 >100
9 230 >100
10 8 >5
然后我可以用一个计数进行聚合查询,按照Range进行分组,得到类似的东西(这些点不会弄乱格式):
Range Total
.>100 6
.>5 4
但是,我想要的就是报告,如下所示:
Range N1 P1 N2 P2
Total 10 100%
.>5 4 40% 6 60%
.>100 6 60% 4 40%
我所做的就是删除组并执行一个outter选择,以我想要的方式对这些列进行求和,并将它们分开,但我只是通过使用range和N1列来实现这一点,所以它看起来像这样:
Range N1
Total 10
.>5 4
.>100 6
我使用的查询(在univoting之前)是:
select [.>5] = sum(case when ([Range] > '>5' then 1 else 0 end)
[.>100] = sum(case when ([Range] > '>100' then 1 else 0 end)
[Total] = count(*)
From tableName
如何让我的结果看起来像这样:
Range N1 P1 N2 P2
Total 10 100%
.>5 4 40% 6 60%
.>100 6 60% 4 40%
注意:我不一定要解开,这只是我发现如何去做的一种方式,我可能有更好的方式。
感谢您的帮助!
答案 0 :(得分:0)
您的结果似乎非常多余。忽略“总计”行,您似乎想要这些结果:
select Range, count(*) as n1,
count(*) * 1.0 / sum(count(*)) over () as p1,
sum(count(*)) over () - count(*) as n2,
1 - count(*) * 1.0 / sum(count(*)) over () as p2
From tableName
group by [Range];
您可以使用grouping sets
添加总计:
select Range, count(*) as n1,
count(*) * 1.0 / sum(count(*)) over () as p1,
sum(count(*)) over () - count(*) as n2,
1 - count(*) * 1.0 / sum(count(*)) over () as p2
From tableName
group by grouping sets ((), ([Range]));
答案 1 :(得分:0)
你好Angra可能是这段代码帮助你,我检查你的场景它返回你期望的结果。
选择[范围] ='> 5',N1 =总和(情况时([范围] ='> 5')然后1其他0结束),P1 = concat(sum(([范围] ='> 5')然后1其他0结束的情况),' 0%') ,N2 = sum(([Range] ='> 100')然后1 else 0 end),P2 = concat(sum(([Range] ='> 100& #39;)然后1其他0结束),' 0%')来自tableName
联合
选择[范围] ='> 100',N1 = sum(情况时([范围] ='> 100')然后1其他0结束),P1 = concat(sum(([范围] ='> 100')然后1其他0结束的情况),' 0%') ,N2 = sum(([Range] ='> 5')然后1 else 0 end),P2 = concat(sum(([Range] ='> 5& #39;)然后1其他0结束),' 0%')来自tableName
联盟
从tableName中选择[Range] =' Total',N1 = count(value),P1 = concat(count(value),' 0%'),null,null
答案 2 :(得分:0)
declare @t table (Id int, Value int, Range varchar(5))
insert into @t values
(1, 101, '>100' ),
(2, 8 , '>5' ),
(3, 330, '>100'),
(4, 230, '>100'),
(5, 8 , '>5'),
(6, 101, '>100'),
(7, 8 , '>5'),
(8, 330, '>100'),
(9, 230, '>100'),
(10, 8 , '>5')
select CASE
WHEN T.RANGE = '>0' THEN 'Total'
else t.range
end as Range,
t.n1,t.p1,
isnull(cast(t.n2 as varchar(6)),'') n2,
ISNULL(cast(t.p2 as varchar(6)),'') p2
from
(
select s.range,
s.n1,
cast(cast(s.n1 as decimal(10,2)) / (select count(*) from @t) *100 as decimal(10,2)) p1,
case
when s.range <> '>0' then (select count(*) from @t where range <> s.range)
end as n2,
case
when s.range <> '>0' then
cast(
cast((select count(*) from @t where range <> s.range) as decimal(10,2)) /
cast((select count(*) from @t) as decimal(10,2)) *100.00
as decimal(10,2))
end as p2
from
(
select t.range,count(*) n1
from @t t
group by range
union
select '>0',count(*)
from @t
) s
) t
order by cast(replace(range,'>','') as int)
结果
Range n1 p1 n2 p2
----- ----------- --------------------------------------- ------ ------
Total 10 100.00
>5 4 40.00 6 60.00
>100 6 60.00 4 40.00