ROW_NUMBER

Numbering rows with ROW_NUMBER

SQLite in your browser
Lesson concept What you'll do
1 / 4

Number the rows in order, or pick the latest loan per member.

ROW_NUMBER() OVER (ORDER BY ...) numbers every row and keeps them all.

The database
11 rows
loan_idbook_idmember_idloan_datereturned
111022026-01-022026-01-22
231012026-02-102026-02-17
3101062026-03-052026-03-21
481012026-04-072026-04-28
561022026-05-202026-06-03
641042026-06-222026-06-29
741062026-08-022026-08-20
871042026-08-112026-09-01
921042026-09-09NULL
1051052026-09-15NULL
1131062026-10-28NULL
Click a name to type it
Your query
 
Hint: click the green edit button on the board, or type it yourself
Query output Ready to run

Run your query to see the result table.

Press the green Run button or Ctrl+Enter.

Study notes

How ROW_NUMBER, OVER works

ROW_NUMBER() OVER (ORDER BY year) numbers every row 1, 2, 3 in year order.

titleyearposition
Frankenstein18181
Dracula18972
Brave New World19323
Dune19654
Carrie19745
The Hunger Games20086

query

SELECT title, year, 
  ROW_NUMBER() OVER (ORDER BY year) AS position
FROM books;

Every row stays: GROUP BY would squash each genre into one row instead.

Recap: window functions side by side
  • What is a window function?

    A function that works across rows but keeps every row: ROW_NUMBER() OVER (ORDER BY year). COUNT and GROUP BY squash rows into one; window functions add a column instead.

  • What goes in OVER?

    ORDER BY says the order to count in. PARTITION BY member_id starts again for each member, like separate counts per group.

  • Why can't WHERE use the number?

    WHERE runs before window functions are worked out. Put the numbering in a WITH step, then filter: WHERE n = 1.

  • What is it used for?

    "The latest loan per member", "the first order per customer", removing duplicates (keep row 1), and numbering pages of results.

  • How is this like Excel?

    Like a running count: =COUNTIF($B$2:B2, B2) filled down numbers each name's rows 1, 2, 3.

Other databases

How other databases do it

The lessons run on SQLite. Most of SQL is the same everywhere; these are the places where this lesson's SQL differs.

Window functions (ROW_NUMBER, RANK, SUM OVER)
DatabaseHowNote
SQLite (these lessons)YesSince SQLite 3.25 (2018).
PostgreSQLYesSince PostgreSQL 8.4.
MySQL / MariaDBYesSince MySQL 8.0. Not in 5.7.
SQL ServerYesROW_NUMBER and RANK since 2005; running totals (SUM OVER ORDER BY) since 2012.
OracleYesSince Oracle 8i; Oracle calls them analytic functions.
Sybase ASENoNot in ASE. Number rows with a self-join or a temporary table with an IDENTITY column.
Keeping number 1 per group
DatabaseHowNote
SQLite (these lessons)WITH ... WHERE n = 1Or a subquery in FROM.
PostgreSQLDISTINCT ON (member_id) ... ORDER BY member_id, loan_date DESCA PostgreSQL shortcut for "first row per group".
MySQL / MariaDBWITH ... WHERE n = 1
SQL ServerWITH ... WHERE n = 1
OracleWITH ... WHERE n = 1Or a subquery in FROM.
Sybase ASENot available

Know someone fighting with a spreadsheet? Send them this page.