Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> MySQL

หาแถวที่มีค่าเหมือนกันในหลายคอลัมน์ด้วย GROUP BY HAVING ใน MySQL

การเตรียมข้อมูล

mysql> CREATE TABLE DemoTable1861 (
    Id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
    Name VARCHAR(20),
    Marks INT
);

mysql> INSERT INTO DemoTable1861(Name, Marks) VALUES
    ('John', 45), ('Chris', 74), ('David', 89), ('Chris', 74), ('John', 49);

ข้อมูลในตาราง

+----+-------+-------+
| Id | Name  | Marks |
+----+-------+-------+
|  1 | John  |    45 |
|  2 | Chris |    74 |
|  3 | David |    89 |
|  4 | Chris |    74 |  -- ซ้ำกับ Id 2
|  5 | John  |    49 |
+----+-------+-------+

หาแถวที่ Name และ Marks เหมือนกันทุกคอลัมน์

mysql> SELECT Id, Name, Marks FROM DemoTable1861
    WHERE (Name, Marks) IN (
        SELECT Name, Marks FROM DemoTable1861
        GROUP BY Name, Marks
        HAVING COUNT(*) > 1
    );

ผลลัพธ์ (เฉพาะ Chris 74 ที่ซ้ำทั้งคู่):

+----+-------+-------+
| Id | Name  | Marks |
+----+-------+-------+
|  2 | Chris |    74 |
|  4 | Chris |    74 |
+----+-------+-------+

การทำงาน

  1. Subquery: GROUP BY Name, Marks → หากลุ่มที่ซ้ำ (COUNT > 1)
  2. Main query: หาแถวที่ (Name, Marks) อยู่ในรายการซ้ำนั้น
  3. (Name, Marks) IN (...) = Row Constructor Comparison

วิธีอื่น: ใช้ Window Function (MySQL 8.0+)

SELECT Id, Name, Marks FROM (
    SELECT *, COUNT(*) OVER (PARTITION BY Name, Marks) AS cnt
    FROM DemoTable1861
) t WHERE cnt > 1;

หาเฉพาะค่า Duplicate (ไม่เอาแถวทั้งหมด)

SELECT Name, Marks, COUNT(*) 
FROM DemoTable1861 
GROUP BY Name, Marks 
HAVING COUNT(*) > 1;

ลบ Duplicate (เก็บแถวแรก)

DELETE t1 FROM DemoTable1861 t1
JOIN DemoTable1861 t2 
  ON t1.Name = t2.Name AND t1.Marks = t2.Marks AND t1.Id > t2.Id;