Ποιος είναι ο καλύτερος τρόπος για την αφαίρεση διπλών γραμμών από έναν αρκετά μεγάλο πίνακα SQL Server
(π.χ. 300.000+ γραμμές);
Οι γραμμές, φυσικά, δεν θα είναι τέλεια διπλότυπα λόγω της ύπαρξης του πεδίου ταυτότητας RowID
.
Πίνακας μου
RowID int not null identity(1,1) primary key,
Col1 varchar(20) not null,
Col2 varchar(2048) not null,
Col3 tinyint not null
Υποθέτοντας ότι δεν υπάρχουν μηδενικά, GROUP BY
τις μοναδικές στήλες και SELECT
το MIN (ή MAX)
RowId ως τη γραμμή που θα κρατήσετε. Στη συνέχεια, απλά διαγράψτε ό,τι δεν είχε row id:
DELETE FROM MyTable
LEFT OUTER JOIN (
SELECT MIN(RowId) as RowId, Col1, Col2, Col3
FROM MyTable
GROUP BY Col1, Col2, Col3
) as KeepRows ON
MyTable.RowId = KeepRows.RowId
WHERE
KeepRows.RowId IS NULL
Σε περίπτωση που έχετε GUID αντί για ακέραιο αριθμό, μπορείτε να αντικαταστήσετε το
MIN(RowId)
με
CONVERT(uniqueidentifier, MIN(CONVERT(char(36), MyGuidColumn)))
Υπάρχει ένα καλό άρθρο σχετικά με την αφαίρεση αντιγράφων στον ιστότοπο υποστήριξης της Microsoft. Είναι αρκετά συντηρητικό - σας βάζουν να κάνετε τα πάντα σε ξεχωριστά βήματα - αλλά θα πρέπει να λειτουργεί καλά σε μεγάλους πίνακες.
Έχω χρησιμοποιήσει self-joins για να το κάνω αυτό στο παρελθόν, αν και πιθανώς θα μπορούσε να γίνει πιο όμορφο με μια ρήτρα HAVING:
DELETE dupes
FROM MyTable dupes, MyTable fullTable
WHERE dupes.dupField = fullTable.dupField
AND dupes.secondDupField = fullTable.secondDupField
AND dupes.uniqueField > fullTable.uniqueField
Εδώ είναι ένα άλλο καλό άρθρο σχετικά με την αφαίρεση αντιγράφων.
Συζητάει γιατί είναι δύσκολο: "Η SQL βασίζεται στη σχεσιακή άλγεβρα, και τα αντίγραφα δεν μπορούν να εμφανιστούν στη σχεσιακή άλγεβρα, επειδή τα αντίγραφα δεν επιτρέπονται σε ένα σύνολο.",
Η λύση του πίνακα temp και δύο παραδείγματα της mysql.
Στο μέλλον πρόκειται να το αποτρέψετε σε επίπεδο βάσης δεδομένων ή από την πλευρά της εφαρμογής. Θα πρότεινα το επίπεδο της βάσης δεδομένων, επειδή η βάση δεδομένων σας θα πρέπει να είναι υπεύθυνη για τη διατήρηση της αναφορικής ακεραιότητας, οι προγραμματιστές απλά θα προκαλέσουν προβλήματα ;)