developer life/database
[mssql] 페이징(paging) 쿼리 OFFSET ROWS FETCH NEXT 과 ROW_NUMBER() OVER()
노는개발자V
2023. 5. 26. 14:49
DECLARE @PAGE_NO INT = 0 -- 페이지 번호
DECLARE @PAGE_SIZE INT = 10 -- 한 페이지에 보여줄 row 수
페이징 쿼리를 만들 때 필요한 건 현재 페이지 번호와 한 화면에 출력될 페이지수가 필요하다.
페이지번호는 뷰단에서 사용자가 누른 페이지번호를 받아서 처리한다.
1. OFFSET ROWS FETCH NEXT(2012 버전부터 사용 가능)
SELECT t1.*
FROM 테이블명 AS t1 WITH(NOLOCK)
INNER JOIN (
SELECT id
FROM 테이블명 WITH(NOLOCK)
ORDER BY reg_date DESC
OFFSET (@PAGE_NO) * @PAGE_SIZE ROWS
FETCH NEXT (@PAGE_SIZE) ROWS ONLY
) AS t2
ON t1.id = t2.id ORDER BY reg_date DESC;
order by로 정렬기준을 정하고 offset을 통해 현재페이지수에 따른 계산으로 몇 개의 행을 가져올지를 정한다.
offset는 건너뛰기를 의미하며 fetch는 몇개의 행을 가져올지를 결정한다.
현재페이지가 0일경우 0개를 건너뛰고 10개를 가져오고 (0~ 10)
1일 경우 10개를 건너뛰고 10개를 가져오는 셈(10~20)이다.
장점으로는 빠르고 간편한 편이지만 단점으로는 top이나 over 등의 특정구문을 사용할 수 없다.
2. ROW_NUMBER() OVER()
SELECT *
FROM
(
SELECT ROW_NUMBER() OVER(ORDER BY reg_date desc) AS rownum
,* FROM 테이블명 lc
) A
WHERE rownum BETWEEN ((@PAGE_NO)*@PAGE_SIZE)+1 AND ((@PAGE_NO+1)*@PAGE_SIZE)
row_number 함수로 조회된 결과물에 순차적 번호를 달아주고 rownum으로 내가 사용할 부분만 가져온다.
장점은 모든 게시물에 번호를 달아주기 때문에 특정 범위의 검색을 할수 있지만 단점으로는 부하를 일으킬 수 있고 속도가 느린 편이다.