Sql server 带条件的SQL Server窗口函数(用于增量加载的where子句)
我们希望以增量方式将数据从一个表加载到另一个表。有可能会有重复的。实际上,它应该非常简单,但随着数据的增加,速度会变慢 最简单的部分是直接提取数据Sql server 带条件的SQL Server窗口函数(用于增量加载的where子句),sql-server,window-functions,row-number,dense-rank,Sql Server,Window Functions,Row Number,Dense Rank,我们希望以增量方式将数据从一个表加载到另一个表。有可能会有重复的。实际上,它应该非常简单,但随着数据的增加,速度会变慢 最简单的部分是直接提取数据 SELECT s.* FROM dbo.source_table s WHERE s.load_datetime > ( SELECT ISNULL(MAX(t.load_datetime) , '0001-01-01') FROM dbo.target_tab
SELECT s.*
FROM dbo.source_table s
WHERE s.load_datetime > ( SELECT ISNULL(MAX(t.load_datetime) , '0001-01-01')
FROM dbo.target_table AS t
)
查询计划非常快速,只识别增量
如果我想删除重复项,我添加了一个稠密的列组
SELECT *
FROM ( SELECT s.*
,DENSE_RANK() OVER ( PARTITION BY s.business_key ORDER BY s.load_datetime ) AS row_no
FROM dbo.source_table s
WHERE s.load_datetime > ( SELECT ISNULL(MAX(t.load_datetime) , '0001-01-01')
FROM dbo.target_table AS t
)
) AS sub
WHERE sub.row_no = 1
问题是,SQL Server总是在对load\u datetime进行筛选之前先执行窗口函数。我改变了所有不同形式的查询,并研究了web以寻求解决方案。我还尝试了交叉应用和CTE:
WITH data
AS ( SELECT s.*
FROM dbo.source_table s
WHERE s.load_datetime > ( SELECT ISNULL(MAX(t.load_datetime) , '0001-01-01')
FROM dbo.target_table AS t
)
)
SELECT *
FROM ( SELECT *
,DENSE_RANK() OVER ( PARTITION BY business_key ORDER BY load_datetime ) AS row_no
FROM data
) AS sub
WHERE sub.row_no = 1
仍然对整个表中的xx mio行进行排序,而不是对增量进行排序
有人知道如何只获取子查询的第一行,而不使用窗口函数来计算整个数据集吗?它需要是没有临时表的SELECT或VIEW
这些是当前的计划:(最快,无重复检查)(对所有5000万行进行排序)(cte相同)
我尝试删除列存储索引并创建有用的非聚集索引。没有效果。仍然在where子句之前进行密集排序 使用这些是当前计划共享您的执行计划:(最快,无重复检查)(对所有5000万行进行排序)(cte相同)执行计划说这是列存储表,我会更新您的标题和问题以包含该信息。@EckhardZemp Dense_Rank将为相同的编号分配相同的排序值。您可能会得到多个子行_no=1。您应该使用行数,而不是密集列。对于Row_Number,即使排序键匹配,分区中的每一行都会得到一个唯一的数字。@SqlZim我刚刚删除了列存储索引,并创建了有用的非聚集索引。没有效果。仍然在where子句之前进行密集排序。韦斯:我两个都试过了。我们的目标是只在增量数据上执行windows功能,而不是在完整数据上。使用这些共享您的执行计划是当前计划:(最快,无重复检查)(对所有5000万行进行排序)(cte相同)执行计划说这是列存储表,我将更新您的标题和问题,以包含该信息。@EckhardZemp\u Rank将为相同的编号分配相同的排序值。您可能会得到多个子行_no=1。您应该使用行数,而不是密集列。对于Row_Number,即使排序键匹配,分区中的每一行都会得到一个唯一的数字。@SqlZim我刚刚删除了列存储索引,并创建了有用的非聚集索引。没有效果。仍然在where子句之前进行密集排序。韦斯:我两个都试过了。目标是只对增量数据执行windows功能,而不是对完整数据执行windows功能。