2017-04-17 93 views
0

我需要一个表格,其名称为偶数个团队,并且这些表格会生成一个锦标赛的时间表,即如果有4个团队:team1,team2,team3和team4该表的名称,那么结果表看起来像下面的在SQL Server中生成锦标赛赛程表

Team Team  Round 
----------------------- 
team1 team2 1 
team 3 team4 1 
team1 team3 2 
team2 team4 2 
team1 team4 3 
team2 team3 3 

我需要使用T-SQL来做到这一点。我曾尝试使用Round Robin Tournament算法,但我不知道如何在T-SQL中实现它。

回答

0

看到,因为没有其他人给了这个答案,我想我也可以告诉你一个使用动态SQL这样的(可能是低效的)方式:

DECLARE @SQL NVARCHAR(MAX) = N''; 
SELECT TOP (SELECT CASE COUNT(*) % 2 WHEN 1 THEN COUNT(*) ELSE COUNT(*) - 1 END FROM dbo.Teams) @SQL += N' UNION ALL 
SELECT * 
FROM 
(
    SELECT TOP (SELECT COUNT(*)/2 FROM T) 
     Team, 
     RN, 
     RoundNum = ' + CAST(N AS NVARCHAR(3)) + N', 
     Match = ROW_NUMBER() OVER (ORDER BY CASE WHEN RN = 1 THEN 0 ELSE 1 END, (RN + ' + CAST(N - 2 AS NVARCHAR(3)) + N') % (SELECT COUNT(*) FROM T)), 
     Slot = 1 
    FROM T 
    ORDER BY CASE WHEN RN = 1 THEN 0 ELSE 1 END, (RN + ' + CAST(N - 2 AS NVARCHAR(3)) + N') % (SELECT COUNT(*) FROM T) 
    UNION ALL 
    SELECT TOP (SELECT COUNT(*)/2 FROM T) 
     Team, 
     RN, 
     RoundNum = ' + CAST(N AS NVARCHAR(3)) + N', 
     Match = ROW_NUMBER() OVER (ORDER BY CASE WHEN RN = 1 THEN 1 ELSE 0 END, (RN + ' + CAST(N - 2 AS NVARCHAR(3)) + N') % (SELECT COUNT(*) FROM T) DESC), 
     Slot = 2 
    FROM T 
    ORDER BY CASE WHEN RN = 1 THEN 1 ELSE 0 END, (RN + ' + CAST(N - 2 AS NVARCHAR(3)) + N') % (SELECT COUNT(*) FROM T) DESC 
) AS T 
' 
FROM (SELECT ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) FROM sys.objects) T(N) 
ORDER BY N; 

SELECT @SQL = N' 
WITH T AS 
(
    SELECT Team, RN = ROW_NUMBER() OVER (ORDER BY Team) 
    FROM dbo.Teams 
    UNION ALL 
    SELECT ''Bye'', COUNT(*) + 1 
    FROM dbo.Teams 
    HAVING COUNT(*) % 2 = 1 
), 
CTE2 AS 
(
' + STUFF(@SQL, 1, 11, '') + N' 
) 
SELECT T1.RoundNum, T1.Match, Team1 = T1.Team, Team2 = T2.Team 
FROM 
(
    SELECT * 
    FROM CTE2 
    WHERE Slot = 1 
) AS T1 JOIN 
(
    SELECT * 
    FROM CTE2 
    WHERE Slot = 2 
) AS T2 
    ON T2.RoundNum = T1.RoundNum 
    AND T2.Match = T1.Match;'; 


EXEC sp_executesql @SQL; 

从本质上讲,它的fix one of the contributors in the first or last column of the table描述在你的维基链接中,通过扎根1并将所有团队转移到1左右。对于奇数团队,它会添加一个“再见”对手。而且它只是在表格中循环N或N-1次(取决于是否有偶数或奇数的球队)。