Sqlserver
 sql >> Datenbank >  >> RDS >> Sqlserver

SQL-Abfrage - Duplikate löschen, wenn mehr als 3 Duplikate vorhanden sind?

with cte as (
  select row_number() over (partition by dupcol1, dupcol2 order by ID) as rn
     from table)
delete from cte
   where rn > 2; -- or >3 etc

Die Abfrage erstellt eine „Zeilennummer“ für jeden Datensatz, gruppiert nach (dupcol1, dupcol2) und sortiert nach ID. Tatsächlich zählt diese Zeilennummer 'Duplikate', die dieselbe dupcol1 und dupcol2 haben, und weist dann die Nummer 1, 2, 3.. N zu, sortiert nach ID. Wenn Sie nur 2 'Duplikate' behalten möchten, müssen Sie diejenigen löschen, denen die Nummern 3,4,.. N zugewiesen wurden und das ist der Teil, den DELLETE.. WHERE rn > 2; übernimmt

Mit dieser Methode können Sie den ORDER BY ändern passend zu Ihrer bevorzugten Reihenfolge (z. B. ORDER BY ID DESC ), sodass die LATEST hat rn=1 , dann ist das vorletzte rn=2 und so weiter. Der Rest bleibt gleich, das DELETE entfernt nur die ältesten, da sie die höchsten Zeilennummern haben.

Im Gegensatz zu diese eng verwandte Frage , je komplexer die Bedingung wird, desto einfacher wird die Verwendung von CTEs und row_number(). Die Leistung kann immer noch problematisch sein, wenn kein richtiger Zugriffsindex vorhanden ist.