ROW_NUMBER für eine eindeutige Reihenfolge
Innerhalb jeder Partition eine deterministische Zeilennummer vergeben
ROW_NUMBER für eine eindeutige Reihenfolge ist eine kostenlose SQL Interview Prep-Lektion auf CoddyKit. Dies ist Lektion 2 von 4. Du kannst die komplette Lektion unten kostenlos lesen – dann übst du sie direkt im Browser mit einem integrierten Code-Editor und einem KI-Tutor rund um die Uhr. Sie ist Teil des SQL Interview Prep-Lernpfads, und dein Fortschritt wird über Web und CoddyKit-App synchronisiert. Der SQL Interview Prep-Kurs umfasst insgesamt 4 Lektionen.
Was ROW_NUMBER garantiert
ROW_NUMBER() weist jeder Zeile innerhalb ihrer Partition eine eindeutige, lückenlose Ganzzahl zu, beginnend bei 1 und entsprechend dem ORDER BY des Fensters. Keine zwei Zeilen erhalten jemals dieselbe Nummer, auch wenn ihre Sortierwerte identisch sind.
Genau diese Eindeutigkeit ist der Grund, warum Interviewer damit Aufgaben wie „eine Zeile pro Gruppe auswählen“ und Deduplizierungsprobleme lösen. Die anderen Ranking-Funktionen (RANK, DENSE_RANK) garantieren bei Gleichständen keine Eindeutigkeit.
Minimale ROW_NUMBER-Abfrage
Die einfachste Form nummeriert eine gesamte Ergebnismenge in einer gewählten Reihenfolge. ROW_NUMBER benötigt immer ein ORDER BY innerhalb von OVER – ohne dieses wäre die Nummerierung beliebig, und die meisten Engines lehnen die Abfrage ab oder geben eine Warnung aus.
Hier ist der zuletzt eingestellte Mitarbeiter die Zeile 1, wenn Sie nach Einstellungsdatum absteigend sortieren.
SELECT
name,
hire_date,
ROW_NUMBER() OVER (ORDER BY hire_date DESC) AS rn
FROM employees;Nummerierung innerhalb von Partitionen
Fügen Sie PARTITION BY hinzu, um die Zeilen innerhalb jeder Gruppe unabhängig voneinander zu nummerieren. Der Zähler wird bei jedem neuen Partitionswert auf 1 zurückgesetzt.
Im Beispiel erhält jede Abteilung ihre eigene Folge 1, 2, 3, sortiert nach Gehalt. Der Bestverdiener jeder Abteilung erhält die Nummer 1 – die Grundlage des Top-N-pro-Gruppe-Musters.
SELECT
department,
name,
salary,
ROW_NUMBER() OVER (
PARTITION BY department
ORDER BY salary DESC
) AS dept_rn
FROM employees;ROW_NUMBER und Gleichstände: Es gibt keine Gleichstände
Ein entscheidender Punkt im Vorstellungsgespräch: Wenn zwei Zeilen gleiche Sortierwerte haben, weist ROW_NUMBER ihnen trotzdem unterschiedliche Nummern zu. Welche Zeile die kleinere Nummer erhält, ist nichtdeterministisch, sofern Sie keine Spalte zur Auflösung des Gleichstands hinzufügen.
RANKwürde Zeilen mit gleichem Wert denselben Rang geben.ROW_NUMBERwählt zwischen ihnen beliebig eine Reihenfolge.
Damit die Ergebnisse reproduzierbar sind, fügen Sie ORDER BY immer einen eindeutigen Tie-Breaker hinzu.
SELECT
name,
salary,
ROW_NUMBER() OVER (
ORDER BY salary DESC, employee_id -- employee_id breaks ties deterministically
) AS rn
FROM employees;Die Regel für deterministische Tie-Breaker
Wenn Ihr ORDER BY keine strikte Reihenfolge festlegt, weil keine Kombination von Spalten eindeutig ist, kann sich die Zeilennummerierung zwischen zwei Ausführungen ändern – selbst bei unveränderten Daten. Interviewer bauen diese Stolperfalle gerne in Fragen zu Paginierung und zum „aktuellsten Datensatz“ ein.
Faustregel: Fügen Sie als letzten Sortierschlüssel einen Primärschlüssel oder eine andere eindeutige Spalte hinzu, wann immer das Ergebnis stabil sein muss.
-- Unstable: many rows can share the same created_at
ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY created_at DESC)
-- Stable: id guarantees a single deterministic winner
ROW_NUMBER() OVER (PARTITION BY user_id ORDER BY created_at DESC, id DESC)Beispiel: Die neueste Bestellung pro Kunde
Eine Standardaufgabe lautet: „Geben Sie für jeden Kunden seine neueste Bestellung zurück.“ Nummerieren Sie die Bestellungen pro Kunde nach Datum absteigend und behalten Sie anschließend in einer äußeren Abfrage rn = 1.
Da ROW_NUMBER pro Partition garantiert genau eine Zeile mit der Nummer 1 liefert, erhalten Sie genau eine Zeile pro Kunde – keine Duplikate, selbst wenn zwei Bestellungen denselben Zeitstempel haben (der Tie-Breaker löst den Gleichstand auf).
SELECT customer_id, order_id, order_date, amount
FROM (
SELECT
customer_id, order_id, order_date, amount,
ROW_NUMBER() OVER (
PARTITION BY customer_id
ORDER BY order_date DESC, order_id DESC
) AS rn
FROM orders
) t
WHERE rn = 1;Beispiel: Zeilen deduplizieren
ROW_NUMBER ist das sauberste Werkzeug zur Deduplizierung. Partitionieren Sie nach den Spalten, die ein Duplikat definieren, sortieren Sie nach einer Präferenzregel und behalten Sie rn = 1.
Hier behandeln wir Zeilen mit derselben E-Mail-Adresse als Duplikate und behalten die am frühesten erstellte Zeile. Alles mit rn > 1 ist ein Duplikat, das Sie löschen oder ignorieren können.
SELECT id, email, created_at
FROM (
SELECT
id, email, created_at,
ROW_NUMBER() OVER (
PARTITION BY email
ORDER BY created_at ASC, id ASC
) AS rn
FROM users
) t
WHERE rn = 1;ROW_NUMBER für die Paginierung
Bevor OFFSET/FETCH allgemein verfügbar war, wurde die Paginierung mit ROW_NUMBER umgesetzt; in SQL Server und vielen ETL-Aufträgen ist das noch immer der Fall. Nummerieren Sie die Zeilen in einer stabilen Reihenfolge und filtern Sie anschließend in einer äußeren Abfrage einen Bereich der nummerierten Zeilen.
Wichtiger Hinweis für Vorstellungsgespräche: Die Paginierung ist nur dann korrekt, wenn die Sortierung deterministisch ist – andernfalls kann dieselbe Zeile auf zwei Seiten erscheinen oder vollständig übersprungen werden.
SELECT *
FROM (
SELECT *, ROW_NUMBER() OVER (ORDER BY created_at, id) AS rn
FROM articles
) t
WHERE rn BETWEEN 21 AND 40; -- page 2, 20 per pageEine Sequenz zum erneuten Ordnen von Daten vergeben
Manchmal benötigen Sie lediglich einen sequenziellen Index, etwa um Zeilen nach einer Sortierung neu zu nummerieren, eine 1..N-Kennzeichnung zu erstellen oder Zeilen mit einer generierten Sequenz zu paaren. ROW_NUMBER über die gewünschte Reihenfolge erzeugt eine saubere, dichte Sequenz ohne Lücken.
So können Sie auch einer beliebigen ungeordneten Menge eine stabile Position für spätere Joins geben.
SELECT
ROW_NUMBER() OVER (ORDER BY score DESC, player_id) AS leaderboard_position,
player_id,
score
FROM scores;ROW_NUMBER im Vergleich zu COUNT für die „n-te Zeile“
Wenn Sie nach „der drittneuesten Bestellung“ oder „der zweiten Zeile“ gefragt werden, verwenden Sie ROW_NUMBER und filtern in einer äußeren Abfrage nach dem exakten Wert. Da die Nummerierung eindeutig ist, liefert rn = 3 genau eine Zeile.
Im Gegensatz dazu gilt: Wenn Sie den zweiten unterschiedlichen Wert möchten, etwa das zweithöchste Gehalt einschließlich Gleichständen, ist ROW_NUMBER das falsche Werkzeug – dafür benötigen Sie DENSE_RANK, das in der nächsten Lektion behandelt wird.
SELECT order_id, order_date
FROM (
SELECT order_id, order_date,
ROW_NUMBER() OVER (ORDER BY order_date DESC, order_id DESC) AS rn
FROM orders
) t
WHERE rn = 3; -- exactly the 3rd most recent orderZusammenfassung der Stolperfallen
Behalten Sie unter dem Druck eines Vorstellungsgesprächs Folgendes im Kopf:
ROW_NUMBERist innerhalb einer Partition immer eindeutig und lückenlos.- Es benötigt ein
ORDER BYinOVER; ohne einen eindeutigen Tie-Breaker sind die Ergebnisse bei Gleichständen nichtdeterministisch. - Es kann nicht in
WHEREgefiltert werden – verwenden Sie eine Unterabfrage oder CTE. - Verwenden Sie es für eine Zeile pro Gruppe, Deduplizierung und Paginierung; verwenden Sie
DENSE_RANK, wenn Gleichstände dieselbe Nummer erhalten sollen.
Schnelltest
Wie geht ROW_NUMBER mit Zeilen um, die beim ORDER BY-Wert gleichauf liegen?
Zusammenfassung: Deterministische Nummerierung
ROW_NUMBER ist Ihr Werkzeug für eine eindeutige, lückenlose Nummerierung innerhalb von Partitionen. Sie haben gelernt:
- Gesamte Ergebnismengen und Gruppen pro Partition zu nummerieren.
- Für deterministische, reproduzierbare Ergebnisse einen eindeutigen Tie-Breaker hinzuzufügen.
- Probleme wie neueste Zeile pro Schlüssel, Deduplizierung, Paginierung und die n-te Zeile zu lösen, indem Sie
rnin einer äußeren Abfrage filtern.
Als Nächstes sehen Sie, wie RANK und DENSE_RANK Gleichständen bewusst dieselbe Nummer geben – und wie sich ihr Verhalten bei Lücken unterscheidet.
Häufig gestellte Fragen
Ist die Lektion „ROW_NUMBER für eine eindeutige Reihenfolge“ kostenlos?
Ja — der vollständige Text von „ROW_NUMBER für eine eindeutige Reihenfolge“ ist hier im Web kostenlos zu lesen. Um sie interaktiv zu üben (integrierter Code-Editor und 24/7 KI-Tutor) und den Rest des SQL Interview Prep-Kurses freizuschalten, upgrade auf CoddyKit PRO. Der SQL Interview Prep-Kurs umfasst insgesamt 4 Lektionen.
Was lerne ich in „ROW_NUMBER für eine eindeutige Reihenfolge“?
Innerhalb jeder Partition eine deterministische Zeilennummer vergeben Du übst SQL Interview Prep mit praktischem Code, den du direkt im Browser ausführst, und ein 24/7 KI-Tutor beantwortet deine Fragen während du die Lektion bearbeitest.
Brauche ich Erfahrung, um SQL Interview Prep zu starten?
Keine Vorkenntnisse erforderlich. SQL Interview Prep auf CoddyKit ist für Anfänger bis fortgeschrittene Lernende strukturiert, sodass du hier starten oder von Anfang an beginnen und in deinem eigenen Tempo voranschreiten kannst. Dies ist Lektion 2 von 4.
Wie lange dauert die Lektion „ROW_NUMBER für eine eindeutige Reihenfolge“?
Die meisten CoddyKit-Lektionen dauern etwa 5–10 Minuten. Jede ist kompakt und interaktiv, sodass du stetig Fortschritte machst und genau dort weitermachst, wo du aufgehört hast – im Web und in der App.
Kann ich in dieser SQL Interview Prep-Lektion Code schreiben und ausführen?
Ja. Jede SQL Interview Prep-Lektion enthält einen integrierten Code-Editor, sodass du echten Code direkt in deinem Browser schreibst und ausführst und sofort KI-Feedback erhältst — ohne lokale Einrichtung erforderlich.
Alle Lektionen in diesem Kurs
- OVER, PARTITION BY und ORDER BY
- ROW_NUMBER für eine eindeutige Reihenfolge
- RANK oder DENSE_RANK bei Gleichständen
- Nach einem Fensterergebnis filtern