我正在使用SQL Server 2014,我有一个表(t1),其中包含超过25,000行的6个数字的列表。
t1的摘录如下:
Id F1 F2 F3 F4 F5 F6
1 5 11 15 21 30 36
2 8 10 21 25 32 39
3 10 18 23 27 28 30
...
我想编写2个案例声明,以执行以下操作:
这是我期望的输出:
Id F1 F2 F3 F4 F5 F6 LastDigit CountLastDigit
1 5 11 15 21 30 36 Yes 4
2 8 10 21 25 32 39 No 0
3 10 18 23 27 28 30 Yes 2
...
我一直坚持在2个case语句后面编写逻辑。任何帮助,将不胜感激。
这是一个有趣的问题。您可以通过横向联接来实现。想法是将数字列取消旋转到行,按最后一位数字进行汇总,并仅保留出现次数最多的内容。然后,您只需要添加一些条件逻辑即可:
select *
from mytable t
cross apply (
select top (1)
case when count(*) = 1 then 'No' else 'Yes' end LastDigit,
case when count(*) = 1 then 0 else count(*) end CountLastDigit
from (values(f1), (f2), (f3), (f4), (f5), (f6)) x(f)
group by f % 10
order by CountLastDigit desc
) z
ID | F1 | F2 | F3 | F4 | F5 | F6 | LastDigit | CountLastDigit-:| -:| -:| -:| -:| -:| -:| :-------- | -------------: 1 | 5 | 11 | 15 | 21 | 30 | 36 |是的2 2 | 8 | 10 | 21 | 25 | 32 | 39 |没有0 3 | 10 | 18 | 23 | 27 | 28 | 30 |是的2
如果要对最高领带数进行求和,则子查询中还需要一个聚合级别:
select *
from mytable t
cross apply (
select
max(LastDigit) LastDigit,
sum(CountLastDigit) CountLastDigit
from (
select top (1) with ties
case when count(*) = 1 then 'No' else 'Yes' end LastDigit,
case when count(*) = 1 then 0 else count(*) end CountLastDigit
from (values(f1), (f2), (f3), (f4), (f5), (f6)) x(f)
group by f % 10
order by CountLastDigit desc
) z
) z
横向连接似乎是正确的方法。作为工作的一部分,我将进行汇总:
select t.*, (case when c.num_duplicates > 0 then 'Yes' else 'No' end) as lastDigit,
coalesce(c.num_duplicates, 0)
from t cross apply
(select sum(cnt) as num_duplicates
from (select f % 10 as digit, count(*) as cnt
from (values (t.f1), (t.f2), (t.f3), (t.f4), (t.f5), (t.f6)) v(f)
group by f % 10
having count(*) > 1
) c
) c;
Here是db <>小提琴。