我有一个不同版本的文件表。除最后一个版本外,文件的所有版本都应标记为已删除。
file_key | path | version | is_deleted
----------+-------+---------+------------
1 | foo/1 | 1 | f <=== wrong
2 | foo/1 | 2 | f <=== wrong
3 | foo/1 | 3 | f
4 | bar/2 | 1 | t
5 | bar/2 | 2 | t
6 | bar/2 | 3 | f
我正在寻找查询以查找前两行并将其标记为is_deleted
。我偶然发现了一些自我加入,结果只有组合,而且#34;&#34;&#34; CTE开始看起来无限递归。
是否有sql解决方案,或者我应该只写一个游标?
答案 0 :(得分:3)
测试数据
DECLARE @t TABLE (file_key INT, [Path] VARCHAR(10),[Version] INT, is_deleted CHAR(1))
INSERT INTO @t
VALUES
(1,'foo/1',1,'f'), (2,'foo/1',2,'f'),(3,'foo/1',3,'f'),
(4,'bar/2',1,'t'),(5,'bar/2',2,'t'),(5,'bar/2',3,'f')
查询(适用于Sql-Server)
;WITH LatestVersions
AS
(
SELECT *, rn = RANK() OVER (PARTITION BY [Path] ORDER BY [Version] DESC)
FROM @t
)
UPDATE LatestVersions
SET is_deleted = 't'
FROM LatestVersions
WHERE rn > 1
结果集
╔══════════╦═══════╦═════════╦════════════╗
║ file_key ║ Path ║ Version ║ is_deleted ║
╠══════════╬═══════╬═════════╬════════════╣
║ 1 ║ foo/1 ║ 1 ║ t ║
║ 2 ║ foo/1 ║ 2 ║ t ║
║ 3 ║ foo/1 ║ 3 ║ f ║
║ 4 ║ bar/2 ║ 1 ║ t ║
║ 5 ║ bar/2 ║ 2 ║ t ║
║ 5 ║ bar/2 ║ 3 ║ f ║
╚══════════╩═══════╩═════════╩════════════╝