sup*_*erB 5 sql t-sql sql-server-2012
这里我有学生拥有RollNumbers及其课程代码的示例数据.
-------------------------
Roll CourseCode
--------------------------
1011 CS201
2213 CS201
3312 CS101
4000 CS201
1011 CS101
5312 ME102
1011 PT101
3312 ME102
Run Code Online (Sandbox Code Playgroud)
结果应该是Coursecode他们的考试日期
例如(排序不同的课程代码)
首先,我选择CS201并将该课程代码指定为日期; 将它放在一个临时表中,然后我选择了CS101并将在临时表中检查此课程代码的RollNumbers是否与临时表中其他任何其他课程代码的RollNumber匹配.
---------------------
Code Date
---------------------
CS101 1
CS201 2
ME102 1
PT101 3
Run Code Online (Sandbox Code Playgroud)
我的代码:
#temp3 包含所有数据(CourseCodes,RollNumbers)#mytemp1 (输出数据)和cursor包含Distinct课程代码
SET @cursor = CURSOR FOR
SELECT DISTINCT coursecode
FROM #temp3
ORDER BY CourseCode
OPEN @cursor
FETCH NEXT
FROM @cursor INTO @cursorid
WHILE @@FETCH_STATUS = 0
BEGIN
BEGIN
SET @j=1
WHILE(@j !=9999999)
BEGIN
IF( SELECT COUNT(*) FROM #temp3 WHERE CourseCode = @cursorid AND RegdNo IN (
SELECT RegdNo FROM #temp3 WHERE CourseCode IN ( SELECT coursecode FROM #myTemp1 WHERE counter1 = @j)
)) = 0
BEGIN
INSERT INTO #myTemp1 VALUES (@cursorid,@j)
SET @j=9999999
END
ELSE
BEGIN
SET @j = @j + 1
END
END
END
FETCH NEXT
FROM @cursor INTO @cursorid
END
CLOSE @cursor
DEALLOCATE @cursor
Run Code Online (Sandbox Code Playgroud)
这段代码工作正常,但花了太多时间(4110222条记录)
任何帮助,将不胜感激
这是一些代码。我相信您的输出有错误,CS101应该先于CS201:
DECLARE @t TABLE ( Roll INT, Code CHAR(5) )
INSERT INTO @t
VALUES ( 1011, 'CS201' ),
( 2213, 'CS201' ),
( 3312, 'CS101' ),
( 4000, 'CS201' ),
( 1011, 'CS101' ),
( 5312, 'ME102' ),
( 1011, 'PT101' ),
( 3319, 'ME102' );
WITH cte1
AS ( SELECT code ,
ROW_NUMBER() OVER ( ORDER BY Code ) AS rn
FROM @t
GROUP BY code
),
cte2
AS ( SELECT code ,
rn ,
1 AS Date
FROM cte1
WHERE rn = 1
UNION ALL
SELECT c1.code ,
c1.rn ,
CASE WHEN EXISTS ( SELECT *
FROM @t a
JOIN @t b ON a.Roll = b.Roll
JOIN cte1 c ON c.rn < c1.rn
AND b.Code = c.code
WHERE a.code = c1.code ) THEN 1
ELSE 0
END
FROM cte1 c1
JOIN cte2 c2 ON c1.rn = c2.rn + 1
),
cte3
AS ( SELECT Code ,
CASE WHEN Date = 0 THEN 1
ELSE SUM(Date) OVER ( ORDER BY rn )
END AS Date
FROM cte2
)
SELECT * FROM cte3
Run Code Online (Sandbox Code Playgroud)
输出:
Code Date
CS101 1
CS201 2
ME102 1
PT101 3
Run Code Online (Sandbox Code Playgroud)
编辑:
cte1将返回:
code rn
CS101 1
CS201 2
ME102 3
PT101 4
Run Code Online (Sandbox Code Playgroud)
主要工作是在 中完成的cte2。它是递归公用表表达式。首先,您从以下位置获取顶部 1 行cte1:
SELECT code ,
rn ,
1 AS Date
FROM cte1
WHERE rn = 1
Run Code Online (Sandbox Code Playgroud)
然后递归进行:
您正在加入cte1并选择以下 rns (2, 3...),并在第一步检查先前代码中的匹配卷cte2中是否有任何卷( ),检查先前代码中的匹配卷中是否有任何卷 ( )在第二步等中。如果存在则返回 1,否则返回 0:CS201CS101ME102CS101, CS201
code rn Date
CS101 1 1
CS201 2 1
ME102 3 0
PT101 4 1
Run Code Online (Sandbox Code Playgroud)
Lastcte3执行以下操作:如果 Date = 0,则返回 1,否则返回前几行(包括当前行)中的日期总和。
编辑1:
由于我的理解不正确,这里再声明一下:
WITH cte
AS ( SELECT code ,
ROW_NUMBER() OVER ( ORDER BY Code ) AS rn
FROM @t
GROUP BY code
)
SELECT co.Code,
DENSE_RANK() OVER(ORDER BY ISNULL(o.Code, co.Code)) AS Date
FROM cte co
OUTER APPLY(SELECT TOP 1 ci.Code
FROM cte ci
WHERE ci.rn < co.rn AND
NOT EXISTS(SELECT * FROM @t
WHERE code = ci.code AND
roll IN(SELECT roll FROM @t WHERE code = co.code)) ORDER BY ci.rn) o
ORDER BY co.rn
Run Code Online (Sandbox Code Playgroud)
输出:
Code Date
CS101 1
CS201 2
ME102 1
PT101 2
Run Code Online (Sandbox Code Playgroud)
编辑2:
这很疯狂,但是,这里的代码似乎有效:
WITH cte
AS ( SELECT * ,
ROW_NUMBER() OVER ( PARTITION BY roll ORDER BY Code ) AS Date
FROM @t
)
SELECT Code ,
MAX(Date) AS Date
FROM cte
GROUP BY Code
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
158 次 |
| 最近记录: |