Untuk menghindari kemungkinan hasil yang tidak terduga ketika menggunakan GROUP BYtanpa fungsi agregat, seperti yang digunakan dalam jawaban yang diterima , karena MySQL bebas untuk mengambil nilai APAPUN dalam kumpulan data yang dikelompokkan ketika tidak menggunakan fungsi agregat [sic] dan masalah dengan ONLY_FULL_GROUP_BY. Harap pertimbangkan untuk menggunakan gabungan pengecualian.
Pengecualian Bergabung - Entitas yang Tidak Mendua
Dengan asumsi nama depan dan nama belakang diindeks secara unik (tidak ambigu) , alternatifnya GROUP BYadalah menyortir menggunakan LEFT JOINuntuk menyaring set hasil, atau dikenal sebagai pengecualian. GABUNG.
Lihat Demonstrasi
Pesanan naik (AZ)
Untuk mengambil nama depan berbeda yang dipesan oleh nama belakang dari AZ
Pertanyaan
SELECT t1.*
FROM table_name AS t1
LEFT JOIN table_name AS t2
ON t1.firstname = t2.firstname
AND t1.lastname > t2.lastname
WHERE t2.id IS NULL;
Hasil
| id | firstname | lastname |
|----|-----------|----------|
| 2 | Bugs | Bunny |
| 1 | John | Doe |
Urutan menurun (ZA)
Untuk mengambil nama depan berbeda yang dipesan oleh nama belakang dari ZA
Pertanyaan
SELECT t1.*
FROM table_name AS t1
LEFT JOIN table_name AS t2
ON t1.firstname = t2.firstname
AND t1.lastname < t2.lastname
WHERE t2.id IS NULL;
Hasil
| id | firstname | lastname |
|----|-----------|----------|
| 2 | Bugs | Bunny |
| 3 | John | Johnson |
Anda kemudian dapat memesan data yang dihasilkan sesuai keinginan.
Pengecualian Bergabung - Entitas Mendua
Jika kombinasi nama depan dan belakang tidak unik (ambigu) dan Anda memiliki beberapa baris dengan nilai yang sama, Anda dapat memfilter hasil yang ditetapkan dengan menyertakan kondisi ATAU pada kriteria GABUNG untuk juga memfilter menurut id.
Lihat Demonstrasi
data table_name
(1, 'John', 'Doe'),
(2, 'Bugs', 'Bunny'),
(3, 'John', 'Johnson'),
(4, 'John', 'Doe'),
(5, 'John', 'Johnson')
Pertanyaan
SELECT t1.*
FROM table_name AS t1
LEFT JOIN table_name AS t2
ON t1.firstname = t2.firstname
AND (t1.lastname > t2.lastname
OR (t1.firstname = t1.firstname AND t1.lastname = t2.lastname AND t1.id > t2.id))
WHERE t2.id IS NULL;
Hasil
| id | firstname | lastname |
|----|-----------|----------|
| 1 | John | Doe |
| 2 | Bugs | Bunny |
Subquery Dipesan
EDIT
Jawaban asli saya menggunakan subquery yang dipesan , ditulis sebelum MySQL 5.7.5 , yang tidak lagi berlaku, karena perubahan denganONLY_FULL_GROUP_BY . Silakan gunakan pengecualian gabungan contoh di atas saja.
Penting juga untuk dicatat; ketika ONLY_FULL_GROUP_BYdinonaktifkan (perilaku asli sebelum MySQL 5.7.5) , penggunaan GROUP BYtanpa fungsi agregat dapat menghasilkan hasil yang tidak terduga, karena MySQL bebas untuk memilih nilai APAPUN dalam kumpulan data yang dikelompokkan [sic] .
Berarti suatu IDatau lastnamenilai dapat diambil yang tidak terkait dengan firstnamebaris yang diambil .
PERINGATAN
Dengan MySQL GROUP BYmungkin tidak menghasilkan hasil yang diharapkan saat digunakan bersamaORDER BY
Lihat Contoh Test Case
Metode implementasi terbaik, untuk memastikan hasil yang diharapkan, adalah dengan memfilter lingkup pengaturan hasil menggunakan subquery yang dipesan.
data table_name
(1, 'John', 'Doe'),
(2, 'Bugs', 'Bunny'),
(3, 'John', 'Johnson')
Pertanyaan
SELECT * FROM (
SELECT * FROM table_name ORDER BY ID DESC
) AS t1
GROUP BY FirstName
Hasil
| ID | first | last |
|----|-------|---------|
| 2 | Bugs | Bunny |
| 3 | John | Johnson |
Perbandingan
Untuk menunjukkan hasil yang tidak terduga saat menggunakan GROUP BYdalam kombinasi denganORDER BY
Pertanyaan
SELECT * FROM table_name GROUP BY FirstName ORDER BY ID DESC
Hasil
| ID | first | last |
|----|-------|-------|
| 2 | Bugs | Bunny |
| 1 | John | Doe |