我发现自己需要获取每个用户最近访问的 N 件事,并且我有一个所有访问的日志表。就像是
CREATE TABLE [AccessLog] ([UserId] UNIQUEIDENTIFIER, [ThingId] UNIQUEIDENTIFIER, [AccessDate] DATETIME)
所以我写了
SELECT [UserId], [ThingId], [SequenceNumber]
FROM (SELECT [UserId], [ThingId], DENSE_RANK()
OVER (PARTITION BY [UserId] ORDER BY [AccessDate] DESC) SequenceNumber
FROM [AccessLog]
) [AccessLog]
WHERE [SequenceNumber] < @N
这是行不通的,因为如果同一用户重复访问同一事物,我们将获得相同的[ThingId]
备份 N 次,而不是[ThingIds]
每个用户 N 次不同的备份。
我对如何实际操作感到困惑。表太大了,如果我必须再次像 2000 一样编写 N 立方连接(一次连接表本身以排除重复副本,第二次生成计数),那么吸取整个表会更快在应用程序代码中处理它。
这几乎就像我想要的
FOR EACH [UserId] IN (SELECT [UserId] IN [User])
SELECT TOP (@N) [UserId], [ThingId]
FROM [AccessLog]
ORDER BY [AccessDate] DESC
但是这种性能也很糟糕,我最好再次将表格读入应用程序代码。
太棒了,所以这是游戏计划。
AccessLog
让我们按UserId
和对表格进行分组ThingId
,这样每个表格只有 1 个唯一行,我们将使用MAX()
聚合函数获取AccessDate
每个表格的最后一行,这样它们就可以在您的窗口函数中进行相对比较。这是一个查询: