MariaDB
 sql >> Teknologi Basis Data >  >> RDS >> MariaDB

7 Cara Mengembalikan Baris Duplikat yang memiliki Kunci Utama di MariaDB

Berikut adalah tujuh cara untuk mengembalikan baris duplikat di MariaDB ketika baris tersebut memiliki kunci utama atau kolom pengenal unik lainnya.

Oleh karena itu, baris duplikat memiliki nilai yang sama persis di semua kolom kecuali kolom pengenal uniknya.

Contoh Data

Kami akan menggunakan data berikut untuk contoh kami:

SELECT * FROM Dogs;

Hasil:

+-------+-----------+----------+
| DogId | FirstName | LastName |
+-------+-----------+----------+
|     1 | Bark      | Smith    |
|     2 | Bark      | Smith    |
|     3 | Woof      | Jones    |
|     4 | Ruff      | Robinson |
|     5 | Wag       | Johnson  |
|     6 | Wag       | Johnson  |
|     7 | Wag       | Johnson  |
+-------+-----------+----------+

Dua baris pertama adalah duplikat (kecuali untuk DogId kolom, yang merupakan kunci utama tabel, dan berisi nilai unik di semua baris). Tiga baris terakhir juga merupakan duplikat (kecuali untuk DogId kolom).

Kolom kunci utama memastikan bahwa tidak ada baris duplikat, yang biasanya merupakan hal yang baik di RDBMS. Namun, menurut definisi ini berarti tidak ada duplikat. Dalam kasus kami, kolom kunci utama adalah angka yang bertambah, dan nilainya tidak memiliki arti dan tidak signifikan. Oleh karena itu, kita perlu mengabaikan baris tersebut jika ingin menemukan duplikat di kolom yang adalah penting.

Opsi 1

Kita dapat menggunakan GROUP BY klausa untuk mengelompokkan kolom menurut kolom signifikannya, lalu gunakan the COUNT() fungsi untuk mengembalikan jumlah baris identik:

SELECT 
    FirstName, 
    LastName, 
    COUNT(*) AS Count
FROM Dogs
GROUP BY FirstName, LastName;

Hasil:

+-----------+----------+-------+
| FirstName | LastName | Count |
+-----------+----------+-------+
| Bark      | Smith    |     2 |
| Ruff      | Robinson |     1 |
| Wag       | Johnson  |     3 |
| Woof      | Jones    |     1 |
+-----------+----------+-------+

Kami dapat mengecualikan kolom kunci utama dengan menghilangkannya dari kueri kami.

Hasilnya memberi tahu kita bahwa ada dua baris berisi Bark Smith dan tiga baris berisi Wag Johnson. Ini adalah duplikat (atau rangkap tiga dalam kasus Wag Johnson). Dua baris lainnya tidak memiliki duplikat.

Opsi 2

Kami dapat mengecualikan non-duplikat dari output dengan HAVING klausa:

SELECT 
    FirstName, 
    LastName, 
    COUNT(*) AS Count
FROM Dogs
GROUP BY FirstName, LastName
HAVING COUNT(*) > 1;

Hasil:

+-----------+----------+-------+
| FirstName | LastName | Count |
+-----------+----------+-------+
| Bark      | Smith    |     2 |
| Wag       | Johnson  |     3 |
+-----------+----------+-------+

Opsi 3

Anda juga dapat memeriksa duplikat pada kolom gabungan. Misalnya, kita dapat menggunakan CONCAT() fungsi untuk menggabungkan dua kolom kami, gunakan DISTINCT kata kunci untuk mendapatkan nilai yang berbeda, lalu gunakan COUNT() berfungsi untuk mengembalikan hitungan:

SELECT
    DISTINCT CONCAT(FirstName, ' ', LastName) AS DogName,
    COUNT(*) AS Count
FROM Dogs
GROUP BY CONCAT(FirstName, ' ', LastName);

Hasil:

+---------------+-------+
| DogName       | Count |
+---------------+-------+
| Bark Smith    |     2 |
| Ruff Robinson |     1 |
| Wag Johnson   |     3 |
| Woof Jones    |     1 |
+---------------+-------+

Opsi 4

Kita dapat menggunakan ROW_NUMBER() fungsi dengan PARTITION BY klausa:

SELECT 
    *,
    ROW_NUMBER() OVER ( 
        PARTITION BY FirstName, LastName 
        ORDER BY FirstName, LastName
        ) AS Row_Number
FROM Dogs;

Hasil:

+-------+-----------+----------+------------+
| DogId | FirstName | LastName | Row_Number |
+-------+-----------+----------+------------+
|     1 | Bark      | Smith    |          1 |
|     2 | Bark      | Smith    |          2 |
|     4 | Ruff      | Robinson |          1 |
|     6 | Wag       | Johnson  |          1 |
|     5 | Wag       | Johnson  |          2 |
|     7 | Wag       | Johnson  |          3 |
|     3 | Woof      | Jones    |          1 |
+-------+-----------+----------+------------+

Ini membuat kolom baru dengan nomor baris yang bertambah setiap kali ada duplikat, tetapi disetel ulang lagi saat ada baris unik.

Dalam hal ini kami tidak mengelompokkan hasil, yang berarti kami dapat melihat setiap baris duplikat, termasuk kolom pengenal uniknya.

Opsi 5

Kami juga dapat menggunakan contoh sebelumnya sebagai ekspresi tabel umum dalam kueri yang lebih besar:

WITH cte AS 
    (
        SELECT 
            *,
            ROW_NUMBER() OVER ( 
                PARTITION BY FirstName, LastName 
                ORDER BY FirstName, LastName
                ) AS Row_Number
        FROM Dogs
    )
SELECT * FROM cte WHERE Row_Number <> 1;

Hasil:

+-------+-----------+----------+------------+
| DogId | FirstName | LastName | Row_Number |
+-------+-----------+----------+------------+
|     2 | Bark      | Smith    |          2 |
|     5 | Wag       | Johnson  |          2 |
|     7 | Wag       | Johnson  |          3 |
+-------+-----------+----------+------------+

Ini mengecualikan non-duplikat dari output, dan mengecualikan satu baris dari setiap duplikat dari output.

Kueri ini dapat digunakan sebagai pendahulu untuk operasi de-duping. Itu dapat menunjukkan kepada kita apa yang akan dihapus jika kita memutuskan untuk menghapus duplikat. Untuk menghilangkan penipuan tabel, yang perlu kita lakukan hanyalah mengganti SELECT * . yang terakhir dengan DELETE .

Opsi 6

Berikut cara yang lebih ringkas untuk mendapatkan hasil yang sama seperti contoh sebelumnya:

SELECT * FROM Dogs 
WHERE DogId IN (
    SELECT DogId FROM Dogs 
    EXCEPT SELECT MIN(DogId) FROM Dogs 
    GROUP BY FirstName, LastName
    );

Hasil:

+-------+-----------+----------+
| DogId | FirstName | LastName |
+-------+-----------+----------+
|     2 | Bark      | Smith    |
|     6 | Wag       | Johnson  |
|     7 | Wag       | Johnson  |
+-------+-----------+----------+

Contoh ini tidak memerlukan pembuatan nomor baris terpisah kita sendiri.

Kita dapat mengganti SELECT * dengan DELETE untuk menghapus duplikat.

Opsi 7

Dan terakhir, inilah opsi lain untuk mengembalikan duplikat:

SELECT * 
FROM Dogs d1, Dogs d2 
WHERE d1.FirstName = d2.FirstName 
AND d1.LastName = d2.LastName
AND d1.DogId <> d2.DogId 
AND d1.DogId = (
    SELECT MAX(DogId) 
    FROM Dogs d3 
    WHERE d3.FirstName = d1.FirstName 
    AND d3.LastName = d1.LastName
);

Hasil:

+-------+-----------+----------+-------+-----------+----------+
| DogId | FirstName | LastName | DogId | FirstName | LastName |
+-------+-----------+----------+-------+-----------+----------+
|     2 | Bark      | Smith    |     1 | Bark      | Smith    |
|     7 | Wag       | Johnson  |     5 | Wag       | Johnson  |
|     7 | Wag       | Johnson  |     6 | Wag       | Johnson  |
+-------+-----------+----------+-------+-----------+----------+

  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. 2 Cara Mengganti Substring di MariaDB

  2. Operator MariaDB MINUS Dijelaskan

  3. Cara mengkonfigurasi SELinux untuk sistem berbasis MySQL (Replikasi MySQL/MariaDB + Galera)

  4. MariaDB LOCALTIME() Dijelaskan

  5. MariaDB CEIL() Dijelaskan