Sql 如何获得三连胜
这是表格:Sql 如何获得三连胜,sql,sql-server,sql-server-2008,Sql,Sql Server,Sql Server 2008,这是表格: ([TeamA],[TeamB],[Win],[date]) ('KKR','HYD','KKR',1), ('KKR','MUM','MUM',2), ('RCB','HYD','HYD',3), ('DEL','PUB','PUB',4), ('RR','PUB','RR',4), ('RR','DEL','RR',5), ('RCB','CSK','CSK',6), ('RR','CSK','RR',7), ('CSK','MUM','MUM',7), ('MUM'
([TeamA],[TeamB],[Win],[date])
('KKR','HYD','KKR',1),
('KKR','MUM','MUM',2),
('RCB','HYD','HYD',3),
('DEL','PUB','PUB',4),
('RR','PUB','RR',4),
('RR','DEL','RR',5),
('RCB','CSK','CSK',6),
('RR','CSK','RR',7),
('CSK','MUM','MUM',7),
('MUM','DEL','MUM',8),
('HYD','PUNE','PUNE',9),
('PUB','DEL','DEL',9),
('KKR','DEL','KKR',10),
('KKR','RCB','KKR',10)
要求的答案应该是连续赢3场的球队和计数。在这里,例如RR和妈妈将连续三次获胜。KKR有3场胜利,但是如果我们看到日期列,它不是连续的3场,因此KKR不应该出现在答案中,输出应该是
RR 1
MUM 1
我的方法可能是以更干净的方式进行:
WITH cte AS
(
SELECT TeamA AS team FROM #tab
UNION
SELECT TeamB FROM #tab
), cte2 AS
(
SELECT c.team
,[opponent] = CASE WHEN c.team = t.teamA THEN t.teamB ELSE t.teamA END
,t.[win]
,t.[day]
,[is_winner] = CASE WHEN c.team = t.[win] THEN 1 ELSE 0 END
FROM cte c
JOIN #tab t
ON c.team = t.teamA
OR c.team = t.teamB
), cte3 AS
(
SELECT team, [day], [is_winner],
r = ROW_NUMBER() OVER (PARTITION BY team ORDER BY [day])
FROM cte2
), cte4 AS
(
SELECT team, Length = MAX(r) - MIN(r) + 1
FROM (SELECT team, r
,rn=r-ROW_NUMBER() OVER (PARTITION BY team ORDER BY r)
FROM cte3
WHERE is_winner = 1) a
GROUP BY team, rn
)
SELECT team, SUM(Length/3) AS [Number_of_hat_tricks]
FROM cte4
WHERE Length >= 3
GROUP BY team;
输出:
╔══════╦══════════════════════╗
║ team ║ Number_of_hat_tricks ║
╠══════╬══════════════════════╣
║ MUM ║ 1 ║
║ RR ║ 1 ║
╚══════╩══════════════════════╝
工作原理:
cte-集合所有团队
cte2-为每支球队寻找对手,并检查球队是否获胜
cte3-添加需求编号
cte4-计算每个岛的长度
最终-获得岛>=3,并将其相加整数除法用于将6个赢的行计算为2,将9个赢的行计算为3,。。。
最后一个想法:
最后一列中的值必须在同一团队中唯一:
('RR','CSK','RR',7)
('CSK','MUM','MUM',7)
CSK vs RR - 7
CSK vs MUM - 7
使用当前数据不可能以稳定的方式对其进行排序。所以应该是日期和时间部分:
CSK vs RR 2015-12-07 10:00
CSK vs MUM 2015-12-07 21:00 -- now we know that it is the second match
缺口和岛屿。计算每个岛的长度。最后的计数是岛的长度除以3整除,丢弃小数部分 我又添加了几行A队和B队,以说明A队4胜,B队7胜,A队4胜,这导致A队和B队的最终计数分别为2和2 样本数据 质疑 通常情况下,你会在一个单独的表中列出一个团队列表,在这里,我将它构建在一个CTE_团队中。CTE_计数在每一个连续的连胜中有3连胜的数量。由于一支球队可能会有多场连胜,请参见a队,我们将进一步总结这一点。团队可以按任意顺序列在TeamA和TeamB列中,因此在交叉应用中的WHERE中有一个OR来捕获这两个变体 因此,对于每个团队,只选择与该团队相关的行。这是通过交叉应用完成的 然后,通过使用不同的分区对行进行两次编号来创建经典的间隙和孤岛。行号的差异给出了组孤岛和间隙 筛选CTE_Teams.Team=CA。Win只留下获胜团队的孤岛 按CTE_团队分组。团队给出岛屿的大小,即连续获胜的次数 查询在SQLServer2008中工作
WITH
CTE_Teams
AS
(
SELECT T.TeamA AS Team
FROM @T AS T
UNION -- sic! not ALL
SELECT T.TeamB AS Team
FROM @T AS T
)
,CTE_Counts
AS
(
SELECT
CTE_Teams.Team
--,CA.Win
--,rn1 - rn2 AS GroupNumber
--,COUNT(*) AS GroupSize
,COUNT(*) / 3 AS FinalCount
FROM
CTE_Teams
CROSS APPLY
(
SELECT
T.Win
,T.dt
,ROW_NUMBER() OVER (PARTITION BY CTE_Teams.Team
ORDER BY T.dt, T.TeamA, T.TeamB) AS rn1
,ROW_NUMBER() OVER (PARTITION BY CTE_Teams.Team, T.Win
ORDER BY T.dt, T.TeamA, T.TeamB) AS rn2
FROM @T AS T
WHERE
T.TeamA = CTE_Teams.Team
OR T.TeamB = CTE_Teams.Team
) AS CA
WHERE
CTE_Teams.Team = CA.Win
GROUP BY
CTE_Teams.Team
,CA.Win
,rn1 - rn2
HAVING COUNT(*) / 3 > 0
)
SELECT
CTE_Counts.Team
,SUM(CTE_Counts.FinalCount) AS FinalCount
FROM CTE_Counts
GROUP BY CTE_Counts.Team
ORDER BY CTE_Counts.Team;
结果
不使用CTE解决此问题的另一种可能方法:
create table #a
(
teama varchar(10), teamb varchar(10), win varchar(10), dat int)
insert into #a
values
('KKR','HYD','KKR',1),
('KKR','MUM','MUM',2),
('RCB','HYD','HYD',3),
('DEL','PUB','PUB',4),
('RR','PUB','RR',4),
('RR','DEL','RR',5),
('RCB','CSK','CSK',6),
('RR','CSK','RR',7),
('CSK','MUM','MUM',7),
('MUM','DEL','MUM',8),
('HYD','PUNE','PUNE',9),
('PUB','DEL','DEL',9),
('KKR','DEL','KKR',10),
('KKR','RCB','KKR',10);
select
team,
win,
row_number() over (partition by team order by dat) matchnum
into #res
from
(
select teamA team, case when teamA = win then 1 else 0 end as win, dat
from #a
union all
select teamB team, case when teamB = win then 1 else 0 end , dat
from #a
)A
order by team,dat
select
match1.team, count(*)/3 + 1 cntHatricks
from #res match1 join #res match2
on match1.team = match2.team and match2.matchnum = match1.matchnum+1
join #res match3 on match1.team = match3.team and match3.matchnum = match1.matchnum+2
where
match1.win = 1 and match2.win = 1 and match3.win = 1
group by match1.team
输出
试试这个简单的查询
select tm,sum(case when win=tm then 1 else 0 end)/3 hattrick from @a a
inner join (select teama tm from @a union select teamb from @a) t on a.win=t.tm
group by tm
having count(distinct dat)>2
资料
) 选择abc,从ipl中选择先赢后输的案例teama
选择b.win,counthatrick/3作为编号
从ipl b加入
选择a.win,算作hatrick
从ipl a在a.win=b.win上加入ipl b
其中a.day嘿,伙计们,我用过这个版本。让我知道这方面是否有任何问题什么是您的dbms、mysql或sql server?以及什么的计数?他们有多少次连续三次获胜?请把你的问题说清楚,我不明白。RR在第4、5、7天获胜。妈妈在第2、7、8天赢了。他们如何获得资格?我看到KKR只有3场胜利。我认为你的例子是错误的。请再说一遍,因为他们已经连续赢了3场比赛,我的意思是说,无论这几天的差距有多大,他们已经连续赢了3场,而KKR还没有赢t@SouravA开始阅读KKR’,‘妈妈’,‘妈妈’,2,它失去了妈妈,所以它有赢-失败-赢-赢正在通过你的个人资料。在5个月的时间内获得22500分!你太棒了!谢谢你,小伙子!这是一个超级快速的反应,效果非常好。我写了一个简短的版本,因为我不知道你用了多少概念。我将分享我的版本
create table #a
(
teama varchar(10), teamb varchar(10), win varchar(10), dat int)
insert into #a
values
('KKR','HYD','KKR',1),
('KKR','MUM','MUM',2),
('RCB','HYD','HYD',3),
('DEL','PUB','PUB',4),
('RR','PUB','RR',4),
('RR','DEL','RR',5),
('RCB','CSK','CSK',6),
('RR','CSK','RR',7),
('CSK','MUM','MUM',7),
('MUM','DEL','MUM',8),
('HYD','PUNE','PUNE',9),
('PUB','DEL','DEL',9),
('KKR','DEL','KKR',10),
('KKR','RCB','KKR',10);
select
team,
win,
row_number() over (partition by team order by dat) matchnum
into #res
from
(
select teamA team, case when teamA = win then 1 else 0 end as win, dat
from #a
union all
select teamB team, case when teamB = win then 1 else 0 end , dat
from #a
)A
order by team,dat
select
match1.team, count(*)/3 + 1 cntHatricks
from #res match1 join #res match2
on match1.team = match2.team and match2.matchnum = match1.matchnum+1
join #res match3 on match1.team = match3.team and match3.matchnum = match1.matchnum+2
where
match1.win = 1 and match2.win = 1 and match3.win = 1
group by match1.team
+------+-------------+
| Team | cntHatricks |
+------+-------------+
| MUM | 1 |
| RR | 1 |
+------+-------------+
select tm,sum(case when win=tm then 1 else 0 end)/3 hattrick from @a a
inner join (select teama tm from @a union select teamb from @a) t on a.win=t.tm
group by tm
having count(distinct dat)>2
declare @a table
(teama varchar(10), teamb varchar(10), win varchar(10), dat int)
insert into @a
values
('KKR','HYD','KKR',1),
('KKR','MUM','MUM',2),
('RCB','HYD','HYD',3),
('DEL','PUB','PUB',4),
('RR','PUB','RR',4),
('RR','DEL','RR',5),
('RCB','CSK','CSK',6),
('RR','CSK','RR',7),
('CSK','MUM','MUM',7),
('MUM','DEL','MUM',8),
('HYD','PUNE','PUNE',9),
('PUB','DEL','DEL',9),
('KKR','DEL','KKR',10),
('KKR','RCB','KKR',10)