2011-04-26 5 views
29

페이지 매김을 설정할 수 있도록 데이터베이스의 총 레코드 수를 반환하고 싶습니다. SQL Server 2008에서 다음 페이징 메서드를 사용할 때 DB에있는 총 레코드 수를 반환하려면 어떻게합니까?ROW_NUMBER를 사용할 때 SQL 서버에서 총 레코드를 반환하십시오.

ALTER PROCEDURE [dbo].[Nop_LoadAllOptimized] 
    (
     @PageSize int = 20, 
     @PageNumber int = 1, 
     @WarehouseCombinationID int = 1, 
     @CategoryId int = 58, 
     @OrderBy int = 0, 
     @TotalRecords int = null OUTPUT 
    ) 
    AS 
    BEGIN 
    WITH Paging AS (
     SELECT rn = (ROW_NUMBER() OVER (
     ORDER BY 
      CASE WHEN @OrderBy = 0 AND @CategoryID IS NOT NULL AND @CategoryID > 0 
      THEN pcm.DisplayOrder END ASC, 
      CASE WHEN @OrderBy = 0 
      THEN p.[Name] END ASC, 
      CASE WHEN @OrderBy = 5 
      THEN p.[Name] END ASC, 
      CASE WHEN @OrderBy = 10 
      THEN wpv.Price END ASC, 
      CASE WHEN @OrderBy = 15 
      THEN wpv.Price END DESC, 
      CASE WHEN @OrderBy = 20 
      THEN wpv.Price END DESC, 
      CASE WHEN @OrderBy = 25 
      THEN wpv.UnitPrice END ASC 
     )), p.*, pcm.DisplayOrder, wpv.Price, wpv.UnitPrice FROM Nop_Product p 
     INNER JOIN Nop_Product_Category_Mapping pcm ON p.ProductID=pcm.ProductID 
     INNER JOIN Nop_ProductVariant pv ON p.ProductID = pv.ProductID 
     INNER JOIN Nop_ProductVariant_Warehouse_Mapping wpv ON pv.ProductVariantID = wpv.ProductVariantID 
     WHERE pcm.CategoryID = @CategoryId AND (wpv.Published = 1 AND pv.Published = 1 AND p.Published = 1 AND p.Deleted = 0) 
     AND wpv.WarehouseID IN (select WarehouseID from Nop_WarehouseCombination where UserWarehouseCombinationID = @WarehouseCombinationID)  
    ) 
    SELECT TOP (@PageSize) * FROM Paging PG 
    WHERE PG.rn > (@PageNumber * @PageSize) - @PageSize 

    SET @TotalRecords = @@ROWCOUNT 

    END 
+1

[row_number를 사용하여 쿼리에서 @@ rowcount를 가져 오는 효율적인 방법] (http://stackoverflow.com/questions/1038506/efficient-way-of-getting-rowcount-from-a-query-using-row -number/4383164 # 4383164) –

+0

@Martin thats 내가 뭘보고 있었는지는하지만 총 행 수를 반환하는 방법을 말해주지 않습니까? – izip

+0

내 의견을 편집하고 링크를 변경했습니다. 어떤 링크를 언급하고 있습니까? SQLServerCentral 하나 또는 StackOverflow 하나? BTW이 내용을 다루는 것은 [SQL Server Central article 2 부] (http://www.sqlservercentral.com/articles/paging/70120/)입니다. –

답변

58

나는 일반적으로 이런 식으로 할 - 정말 성능의 관점에서 매우 효율적 여부를 확인하지 : 기본적으로

WITH YourCTE AS 
(
    SELECT 
     (list of columns), 
     ROW_NUMBER() OVER (ORDER BY ......) AS 'RowNum' 
    FROM dbo.YourBaseTable 
) 
SELECT 
    *, 
    (SELECT MAX(RowNum) FROM YourCTE) AS 'TotalRows' 
FROM 
    YourCTE 
WHERE 
    RowNum BETWEEN 101 AND 150 

에서, RowNum 값 (행의 총을 통해 값 1을해야합니다 CTE에 PARTITION BY이없는 경우) 을 선택하면 총 행 수가 표시됩니다.

+1

감사합니다. TotalRows를 저장 프로 시저의 출력 매개 변수에 어떻게 할당합니까? 그것은 두 가지 방법, 당신과 Martins,하지만 내 데이터 집합의 새 열보다는 param로 반환하고 싶습니다. 편집 : @TotalRecords = PG.TotalRows – izip

+1

굉장 ....... :) – Umer

+1

매우 영리합니다! 나를 위해 위대한 (그리고 빠른) 작품. –

24

글쎄 과거에는 #temp 개의 테이블을 사용했지만 다른 솔루션은 Count(..) OVER()을 사용하여 며칠 전 총 행 수를 찾았습니다.

SELECT COUNT(id) OVER() [Total], ROW_NUMBER() OVER(ORDER BY id DESC) [RowNo] 
, [other columns] 
FROM Table 

참조 페이지 here이다 : 그것은는 다음과 같이 작동합니다.

+0

이것은 지금까지이 문제에서 발견 된 최상의 해결책입니다. 쿼리 실행 시간에 큰 영향을주지 않는 이점이 있습니다. – bcleary

+1

여기서 문제는 WHERE 절에서 RowNo를 사용할 수 없다는 것입니다. – Fedor

+0

고마워요. 당신은 내 시간을 절약 .. –

관련 문제