Sign Up

Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.

Have an account? Sign In

Have an account? Sign In Now

Sign In

Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.

Sign Up Here

Forgot Password?

Don't have account, Sign Up Here

Forgot Password

Lost your password? Please enter your email address. You will receive a link and will create a new password via email.

Have an account? Sign In Now

You must login to ask a question.

Forgot Password?

Need An Account, Sign Up Here

Please briefly explain why you feel this question should be reported.

Please briefly explain why you feel this answer should be reported.

Please briefly explain why you feel this user should be reported.

Sign InSign Up

The Archive Base

The Archive Base Logo The Archive Base Logo

The Archive Base Navigation

  • Home
  • SEARCH
  • About Us
  • Blog
  • Contact Us
Search
Ask A Question

Mobile menu

Close
Ask a Question
  • Home
  • Add group
  • Groups page
  • Feed
  • User Profile
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Buy Points
  • Users
  • Help
  • Buy Theme
  • SEARCH
Home/ Questions/Q 5940165
In Process

The Archive Base Latest Questions

Editorial Team
  • 0
Editorial Team
Asked: May 22, 20262026-05-22T15:55:50+00:00 2026-05-22T15:55:50+00:00

I have identified a way to get fast paged results from the database using

  • 0

I have identified a way to get fast paged results from the database using CTEs and the Row_Number function, as follows…

DECLARE @PageSize INT = 1
DECLARE @PageNumber INT = 2

DECLARE @Customer TABLE (
  ID       INT IDENTITY(1, 1),
  Name     VARCHAR(10),
  age      INT,
  employed BIT)

INSERT INTO @Customer
    (name,age,employed)
SELECT 'bob',21,1
    UNION ALL
SELECT 'fred',33,1
    UNION ALL
SELECT 'joe',29,1
    UNION ALL
SELECT 'sam',16,1
    UNION ALL
SELECT 'arthur',17,0;


WITH cteCustomers
     AS ( SELECT
            id,
            Row_Number( ) OVER(ORDER BY Age DESC) AS Row
          FROM   @Customer
          WHERE  employed = 1 
     /*Imagine I've joined to loads more tables with a really complex where clause*/
     )       

SELECT
  name,
  age,
  Total = ( SELECT
              Count( id )
            FROM   cteCustomers )
FROM       cteCustomers
INNER JOIN @Customer cust
  /*This is where I choose the columns I want to read, it returns really fast!*/
  ON cust.id = cteCustomers.id
WHERE      row BETWEEN ( @PageSize * @PageNumber - 1 ) AND ( @PageSize * ( @PageNumber ) )
ORDER      BY row ASC

Using this technique the returned results is really really fast even on complex joins and filters.

To perform paging I need to know the Total Rows returned by the full CTE. I have “Bodged” this by putting a column that holds it

Total = ( SELECT
              Count( id )
            FROM   cteCustomers )

Is there a better way to return the total in a different result set without bodging it into a column? Because it’s a CTE I can’t seem to get it into a second result set.

  • 1 1 Answer
  • 0 Views
  • 0 Followers
  • 0
Share
  • Facebook
  • Report

Leave an answer
Cancel reply

You must login to add an answer.

Forgot Password?

Need An Account, Sign Up Here

1 Answer

  • Voted
  • Oldest
  • Recent
  • Random
  1. Editorial Team
    Editorial Team
    2026-05-22T15:55:51+00:00Added an answer on May 22, 2026 at 3:55 pm

    Without using a temp table first, I’d use a CROSS JOIN to reduce the risk of row by row evaluation on the COUNT

    To get total row, this needs to happen separately to the WHERE

    WITH cteCustomers
         AS ( SELECT
                id,
                Row_Number( ) OVER(ORDER BY Age DESC) AS Row
              FROM   @Customer
              WHERE  employed = 1 
         /*Imagine I've joined to loads more tables with a really complex where clause*/
         )       
    
    SELECT
      name,
      age,
      Total
    FROM       cteCustomers
    INNER JOIN @Customer cust
      /*This is where I choose the columns I want to read, it returns really fast!*/
      ON cust.id = cteCustomers.id
    
    CROSS JOIN
    
    (SELECT Count( *) AS Total FROM   cteCustomers ) foo
    
    WHERE      row BETWEEN ( @PageSize * @PageNumber - 1 ) AND ( @PageSize * ( @PageNumber ) )
    ORDER      BY row ASC
    

    However, this isn’t guaranteed to give accurate results as demonstrated here:
    can I get count() and rows from one sql query in sql server?

    Edit: after a few comments.

    How to avoid a CROSS JOIN

    WITH cteCustomers
         AS ( SELECT
                id,
                Row_Number( ) OVER(ORDER BY Age DESC) AS Row,
                COUNT(*) OVER () AS Total --the magic for this edit
              FROM   @Customer
              WHERE  employed = 1 
         /*Imagine I've joined to loads more tables with a really complex where clause*/
         )       
    
    SELECT
      name,
      age,
      Total
    FROM       cteCustomers
    INNER JOIN @Customer cust
      /*This is where I choose the columns I want to read, it returns really fast!*/
      ON cust.id = cteCustomers.id
    WHERE      row BETWEEN ( @PageSize * @PageNumber - 1 ) AND ( @PageSize * ( @PageNumber ) )
    ORDER      BY row ASC
    

    Note: YMMV for performance depending on 2005 or 2008, Service pack etc

    Edit 2:

    SQL Server Central shows another technique where you have reverse ROW_NUMBER. Looks useful

    • 0
    • Reply
    • Share
      Share
      • Share on Facebook
      • Share on Twitter
      • Share on LinkedIn
      • Share on WhatsApp
      • Report

Sidebar

Related Questions

I have identified this call as a bottleneck in a high pressure function. graphics.DrawImage(smallBitmap,
We have an WCF application which uses NHibernate to query data from the database.
Have just started using Google Chrome , and noticed in parts of our site,
Have just started using Visual Studio Professional's built-in unit testing features, which as I
The following snippet is from a little app I wrote using the Qt framework.
I have this working definition: IDENTIFIER [a-zA-Z][a-zA-Z0-9]* I don't want to keep repeating the
I have a digital certificate that identifies a user. I need to use it
In a C# application I am working on I have a very long identifier
I'm matching identifiers, but now I have a problem: my identifiers are allowed to
Have you ever seen any of there error messages? -- SQL Server 2000 Could

Explore

  • Home
  • Add group
  • Groups page
  • Communities
  • Questions
    • New Questions
    • Trending Questions
    • Must read Questions
    • Hot Questions
  • Polls
  • Tags
  • Badges
  • Users
  • Help
  • SEARCH

Footer

© 2021 The Archive Base. All Rights Reserved
With Love by The Archive Base

Insert/edit link

Enter the destination URL

Or link to existing content

    No search term specified. Showing recent items. Search or use up and down arrow keys to select an item.