C# SQL查询跟踪问题

C# SQL查询跟踪问题,c#,.net,tsql,sql-server-2008,paging,C#,.net,Tsql,Sql Server 2008,Paging,好吧,这是我的问题 用户可以进入我的站点,一次检索8条记录,然后他/她可以选择加载更多记录。这8条记录可以通过传递到proc的参数进行排序。现在,当我在前端得到这8条记录时,我有它们的ID(显然对用户来说是隐藏的),但是它们的ID没有任何特定的顺序,因为这些记录是按各种可能的东西排序的 当他们单击“加载更多”时,我应该能够从数据库中获取下8条记录,排序方式与前8条相同 例如,“给我按年龄排序的前8条记录”。->单击加载更多->给我接下来的8条最古老的记录,而不显示我刚才看到的记录 如何调用pro

好吧,这是我的问题

用户可以进入我的站点,一次检索8条记录,然后他/她可以选择加载更多记录。这8条记录可以通过传递到proc的参数进行排序。现在,当我在前端得到这8条记录时,我有它们的ID(显然对用户来说是隐藏的),但是它们的ID没有任何特定的顺序,因为这些记录是按各种可能的东西排序的

当他们单击“加载更多”时,我应该能够从数据库中获取下8条记录,排序方式与前8条相同

例如,“给我按年龄排序的前8条记录”。->单击加载更多->给我接下来的8条最古老的记录,而不显示我刚才看到的记录

如何调用proc并确保第一个结果集中没有返回任何结果?出于效率原因,我一次只想返回8条记录

SELECT TOP 8
      m.message,
      m.votes,
      (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 as distance,
      m.location,
      datediff(hour,m.timestamp, getdate()) as age,
      m.messageId,
      ml.voted,
      ml.flagged
    FROM
      tblMessages m
    left join tblIPMessageLink ml on m.messageid = ml.messageid
    WHERE
      m.timestamp >= DATEADD(day, DATEDIFF(day, 0, @date), 0)
      and
      m.timestamp < DATEADD(day, DATEDIFF(day, 0, @date), 1)
      ORDER BY
        CASE WHEN @sort = 'votes1' THEN m.votes END DESC,
        CASE WHEN @sort = 'votes2' THEN m.votes END ASC,
        CASE WHEN @sort = 'age1' THEN datediff(hour,m.timestamp, getdate()) END ASC,
        CASE WHEN @sort = 'age2' THEN datediff(hour,m.timestamp, getdate()) END DESC,
        CASE WHEN @sort = 'distance1' THEN (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 END ASC,
        CASE WHEN @sort = 'distance2' THEN (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 END DESC
      END
选择前8名
m、 信息,
m、 投票,
(地理:点(@纬度,@经度,4326).STDistance(m.Point))*0.000621371192237334作为距离,
m、 位置,
datediff(小时,m.timestamp,getdate())作为年龄,
m、 messageId,
ml.投票,
标记的
从…起
TBL消息m
m.messageid=ml.messageid上的左连接tblIPMessageLink ml
哪里
m、 时间戳>=日期添加(日期,日期差异(日期,0,@date),0)
和
m、 时间戳<日期添加(日期,日期差异(日期,0,@date),1)
订购人
当@sort='votes1'然后m.DESC结束时,
当@sort='votes2'时,则m.vots结束ASC,
当@sort='age1'然后datediff(hour,m.timestamp,getdate())结束ASC时,
当@sort='age2'然后datediff(hour,m.timestamp,getdate())结束DESC时,
当@sort='distance1'时,则为(地理::点(@lation,@longitude,4326).STDistance(m.Point))*0.000621371192237334 END ASC,
当@sort='distance2'然后(地理::点(@纬度,@经度,4326).STDistance(m.Point))*0.000621371192237334 END DESC
结束
这是我目前的问题。如何将其更改为与分页一起使用?

David Hayden对分页有自己的看法。您只需要跟踪记录数和偏移量

此外,每次加载更多的记录时,您仍然需要合并并使用客户端上的记录

这是那篇文章中的SP

CREATE PROCEDURE dbo.ShowLog
    @PageIndex INT, 
    @PageSize INT 
AS

BEGIN 

WITH LogEntries AS ( 
SELECT ROW_NUMBER() OVER (ORDER BY Date DESC)
AS Row, Date, Description 
FROM LOG)

SELECT Date, Description
FROM LogEntries 
WHERE Row between 
(@PageIndex - 1) * @PageSize + 1 and @PageIndex*@PageSize



END 
使用行号

范例

呼叫1

;WITH cte AS(SELECT *,row_number() OVER( ORDER BY name) AS rows FROM sysobjects)

SELECT * FROM cte WHERE ROWS BETWEEN 1 AND 8
ORDER BY rows
呼叫2

;WITH cte AS(SELECT *,row_number() OVER( ORDER BY name) AS rows FROM sysobjects)

SELECT * FROM cte WHERE ROWS BETWEEN 9 AND 16
ORDER BY rows
当然,您希望使用参数而不是硬编码数字,这样您可以重用查询,如果列可以任意排序,那么您可能需要使用动态SQL

编辑,下面是它的外观,您可能还希望返回最大行数,以便知道可能返回的行数 此外,还可以使每页的行数动态,在这种情况下

其中@StartRow和(@StartRow+@RowsPerPage)之间的行-1

请务必阅读,了解如何优化此功能,以获得计划重用和更好的总体计划

不管怎样,这是程序,当然没有经过测试,因为我不能在这里运行它

DECLARE @StartRow INT,@EndRow INT
--SELECT @StartRow =1, @EndRow = 8


;WITH cte AS (SELECT ROW_NUMBER() OVER (ORDER BY
        CASE WHEN @sort = 'votes1' THEN m.votes END DESC,
        CASE WHEN @sort = 'votes2' THEN m.votes END ASC,
        CASE WHEN @sort = 'age1' THEN datediff(hour,m.timestamp, getdate()) END ASC,
        CASE WHEN @sort = 'age2' THEN datediff(hour,m.timestamp, getdate()) END DESC,
        CASE WHEN @sort = 'distance1' THEN (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 END ASC,
        CASE WHEN @sort = 'distance2' THEN (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 END DESC
      END) AS rows 
      m.message,
      m.votes,
      (geography::Point(@latitude, @longitude, 4326).STDistance(m.point)) * 0.000621371192237334 as distance,
      m.location,
      datediff(hour,m.timestamp, getdate()) as age,
      m.messageId,
      ml.voted,
      ml.flagged
    FROM
      tblMessages m
    left join tblIPMessageLink ml on m.messageid = ml.messageid
    WHERE
      m.timestamp >= DATEADD(day, DATEDIFF(day, 0, @date), 0)
      and
      m.timestamp < DATEADD(day, DATEDIFF(day, 0, @date), 1)
      )


     SELECT * 
     FROM cte WHERE ROWS BETWEEN @StartRow AND @EndRow
    ORDER BY rows
声明@StartRow INT,@EndRow INT
--选择@StartRow=1、@EndRow=8
;将cte设置为(按顺序选择上方的行号()
当@sort='votes1'然后m.DESC结束时,
当@sort='votes2'时,则m.vots结束ASC,
当@sort='age1'然后datediff(hour,m.timestamp,getdate())结束ASC时,
当@sort='age2'然后datediff(hour,m.timestamp,getdate())结束DESC时,
当@sort='distance1'时,则为(地理::点(@lation,@longitude,4326).STDistance(m.Point))*0.000621371192237334 END ASC,
当@sort='distance2'然后(地理::点(@纬度,@经度,4326).STDistance(m.Point))*0.000621371192237334 END DESC
结束)作为行
m、 信息,
m、 投票,
(地理:点(@纬度,@经度,4326).STDistance(m.Point))*0.000621371192237334作为距离,
m、 位置,
datediff(小时,m.timestamp,getdate())作为年龄,
m、 messageId,
ml.投票,
标记的
从…起
TBL消息m
m.messageid=ml.messageid上的左连接tblIPMessageLink ml
哪里
m、 时间戳>=日期添加(日期,日期差异(日期,0,@date),0)
和
m、 时间戳<日期添加(日期,日期差异(日期,0,@date),1)
)
选择*
来自cte,其中@StartRow和@EndRow之间的行
按行排序

我对如何使用这个有点困惑。那么我是否需要将StartRow和EndRow传递给proc?跟踪我使用的是哪一个?是的,sql server对clientokay一无所知,所以将其设置为(1,8)只是一个示例。所以我会在下一次运行时将其设置为(9,16),等等。?