Transact sql查询性能建议

时间:2013-07-18 14:45:59

标签: sql-server performance tsql

我有2个选择查询。第一个执行网格分页选择(每页25行)(using TOP @pagesize*@pagenum EXCEPT TOP @pagesize*(@pagenum-1) construction)。第二个查询总行数。

那么,WITH AS构造会增加两个分开的查询的性能,如果是这样,为什么呢?请注意,该查询包含多个列,INNER JOIN和WHERE条件。

2 个答案:

答案 0 :(得分:1)

  1. WITH part for self对性能没有帮助。它使查询更容易理解。
  2. 如果我理解正确,则计数适用于所有行。如果您将所有行都发送到客户端,则可以保存第二个调用,但在大多数情况下,它会更昂贵。
  3. 使用top X只获取最后的X / Y行是一个坏主意。您应该添加一个自动编号,然后选择自动编号在所需范围内的行。

    SELECT ROW_NUMBER()OVER(ORDER BY [Something] DESC)FROM ... 哪个[RowNumber]在10和20之间

答案 1 :(得分:0)

或者,如果您使用ORDER BY ... OFFSET而不是TOP ... ORDER BY您可以使用COUNT(*)OVER()来获取所有行而不管分页。否则,您必须使用WITH(与您一样)隔离数据,并使用第二个表以及其他任何内容(行号,页面,总页面等)进行分页。

没有偏移的示例:

    DECLARE @page INT = 1, @rows INT = 5

    ;WITH data AS  (SELECT * FROM mytable where  id = 454545) --possible filters

          ,rows ([page], [pages], [rows]) AS
          (
          SELECT @page, CEILING(CAST(COUNT(*) AS float)/@rows), COUNT(*) FROM data
          )
          SELECT TOP (@rows) *
          FROM ( SELECT row_number() OVER (ORDER BY data.id) rowNumber, * FROM rows, data ) pagination
          WHERE rowNumber > (@page - 1) * @rows
          order by rowNumber

偏移的示例:

DECLARE @page INT = 1, @rows INT = 5

    SELECT 
    row_number() OVER (order by id ) rowNumber,@page Page,(CEILING(CasT(COUNT(*) OVER () as float)/@rows)) Pages,
    COUNT(*) OVER () Rows, *

    from mytable where  id = 454545 --possible filters
    order by rowNumber 
    OFFset (@page-1)*@rows rows 
    FETCH NEXT @rows rows ONLY

在这两种情况下,请确保订单是绝对的,否则您的分页无法保证