【问题标题】:I wish to put this condition in a more sargable way我希望以更可悲的方式提出这个条件
【发布时间】:2020-10-23 03:12:39
【问题描述】:

在我的 sql server 2017 标准 CU 20 中,有一个经常执行的查询具有这种可怕的情况:

AND F.progressive_invoice % @numberofservicesInstalled = @idService

有没有数学方法可以让sql server更方便?

查询持续 240 到 500 毫秒 你能帮我做得更好吗?请

【问题讨论】:

  • 也许足以把所有的操作放到等号右边(=)

标签: sql-server performance tsql sql-server-2017


【解决方案1】:

你觉得这里有什么特别可怕

这个查询执行得很差吗?你确定这是造成这种情况的原因吗?

这个%modulo operator

SELECT  13 % 5 => Remainder is 3

--这与您的代码所做的大致相同:

DECLARE @Divisor INT=5; --Switch this value
DECLARE @CompareRemainder INT=3;
SELECT CASE WHEN 13 % @Divisor = @CompareRemainder THEN 'Remainder matches variable' ELSE 'no match' END;

您的代码行将告诉引擎计算F.progressive_invoice 和变量@numberofservicesInstalled 的整数除法,然后选择余数。此计算的结果与变量@idService 进行比较。

由于必须对每个值进行此计算,因此索引在这里无济于事...

我不认为,这可以说 更sargable

更新

在您建议的评论中,更改等号运算符后面的代码可能会有所帮助。不,这无济于事。

我试图想出一个有意义的含义... 服务的编号(或者 - 正如变量所暗示的 - 它的id)以某种方式隐藏 在发票号码中?

执行计划和行估计:

引擎会看到,这必须为所有行计算。在您必须执行此操作之前强制执行任何其他过滤器会有所帮助。但你表现得不够。我们看到的这行代码只是条件的一部分……

索引和统计数据肯定也会发挥作用......

【讨论】:

  • 查询计划高估了很多在这种情况下返回的值,如果你可以把操作放在=运算符的右边,结果应该会更好
  • 查询是由程序员继承的,幸运的是它在一个存储过程中,但我不知道它的用途。这是解释的字段:F.progressive_invoice 是发票上渐进的数字,numberofservicesInstalled 是客户端上的服务数量,idService 是服务的 ID。
  • 明天我可以和你分享计划
  • @GabrieleD'Onufrio 究竟是什么意思“进步”? @idService 的最大值是多少? @numberofservicesInstalled 的最大值是多少?在一列中隐藏两个值似乎是一种奇怪的方式......
  • @GabrieleD'Onufrio,这是一种奇怪的编码服务的方式,我将*输入发票号码,不是吗?
【解决方案2】:

对您的直接问题的简短回答是否定的。您不能重新排列此表达式以使其成为 sargable 谓词。至少,不是使用有限且与@numberofservicesinstalled 的可能值无关的构造。

【讨论】:

    猜你喜欢
    • 2013-12-11
    • 1970-01-01
    • 1970-01-01
    • 2021-03-05
    • 2020-07-12
    • 2010-12-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多