Il modo più semplice è con un CTE (espressione di tabella comune). Uso questo metodo quando ho dati grezzi da importare; la prima cosa che faccio per disinfettarlo è assicurarmi che non ci siano duplicati, che ho una sorta di handle univoco per ogni riga.
Riepilogo:
WITH numbered AS (
SELECT ROW_NUMBER() OVER(PARTITION BY [dupe-column-list] ORDER BY [dupe-column-list]) AS _dupe_num FROM [table-name] WHERE 1=1
)
DELETE FROM numbered WHERE _dupe_num > 1;
La parte "dupe-column-list" è dove elenchi tutte le colonne coinvolte in cui desideri che i valori siano univoci. L'ORDINE PER è dove decidi, all'interno di una serie di duplicati, quale riga "vince" e quale viene eliminata. (Il "WHERE 1=1" è solo un'abitudine personale.)
Il motivo per cui funziona è perché Sql Server mantiene un riferimento univoco interno a ciascuna riga di origine selezionata nel CTE. Quindi, quando DELETE viene eseguito, conosce la riga esatta da eliminare, indipendentemente da ciò che hai inserito nell'elenco di selezione del tuo CTE. (Se sei nervoso, puoi cambiare "DELETE" in "SELECT *", ma dal momento che hai righe duplicate, non ti aiuterà; se potessi identificare in modo univoco ogni riga, non leggeresti questo .)
Esempio:
CREATE TABLE ##_dupes (col1 int, col2 int, col3 varchar(50));
INSERT INTO ##_dupes
VALUES (1, 1, 'one,one')
, (2, 2, 'two,two')
, (3, 3, 'three,three')
, (1, 1, 'one,one')
, (1, 2, 'one,two')
, (3, 3, 'three,three')
, (1, 1, 'one,one')
, (1, 2, '1,2');
Delle 8 righe, ne hai 5 coinvolte con problemi duplicati; 3 righe devono essere rimosse. Puoi vedere i problemi con questo:
SELECT col1
, col2
, col3
, COUNT(1) AS _total
FROM ##_dupes
WHERE 1=1
GROUP BY col1, col2, col3
HAVING COUNT(1) > 1
ORDER BY _total DESC;
Ora esegui la seguente query per rimuovere i duplicati, lasciando 1 riga da ogni set di duplicati.
WITH numbered AS (
SELECT ROW_NUMBER() OVER(PARTITION BY col1, col2, col3 ORDER BY col1, col2, col3) AS _dupe_num FROM ##_dupes WHERE 1=1
)
DELETE FROM numbered WHERE _dupe_num > 1;
Ora ti rimangono 5 righe, nessuna delle quali è duplicata.