J'ai le tableau suivant appelé questions:
ID | asker
1 | Bob
2 | Bob
3 | Marley
Je veux sélectionner chaque demandeur une seule fois et s'il y a plusieurs demandeurs portant le même nom, sélectionnez celui du plus haut identifiant Donc, les résultats attendus:
ID | asker
3 | Marley
2 | Bob
J'utilise la requête suivante:
SELECT * FROM questions GROUP by questions.asker ORDER by questions.id DESC
J'obtiens le résultat suivant:
ID | asker
3 | Marley
1 | Bob
Donc, il sélectionne le premier 'Bob' qu'il rencontre au lieu du dernier.
Merci
Si vous voulez la dernière id
pour chaque asker
, utilisez une fonction d'agrégat:
SELECT max(id) as id,
asker
FROM questions
GROUP by asker
ORDER by id DESC
La raison pour laquelle vous obteniez un résultat inhabituel est que MySQL utilise une extension à GROUP BY
qui permet aux éléments d'une liste de sélection d'être non agrégés et non inclus dans la clause GROUP BY. Cela peut toutefois conduire à des résultats inattendus car MySQL peut choisir les valeurs renvoyées. (Voir Extensions MySQL vers GROUP BY )
À partir de la documentation MySQL:
MySQL étend l'utilisation de GROUP BY afin que la liste de sélection puisse faire référence à des colonnes non agrégées non nommées dans la clause GROUP BY. ... Vous pouvez utiliser cette fonctionnalité pour améliorer les performances en évitant le tri et le regroupement inutiles des colonnes. Toutefois, ceci est utile principalement lorsque toutes les valeurs de chaque colonne non agrégée non nommées dans GROUP BY sont identiques pour chaque groupe. Le serveur est libre de choisir n'importe quelle valeur de chaque groupe. Par conséquent, à moins d'être identiques, les valeurs choisies sont indéterminées. De plus, la sélection des valeurs de chaque groupe ne peut pas être influencée par l'ajout d'une clause ORDER BY. Le tri du jeu de résultats a lieu une fois les valeurs choisies et ORDER BY n'affecte pas les valeurs choisies par le serveur.
Normalement, MySQL n'autorise le groupe que par ordre croissant. Nous pouvons donc commander des enregistrements avant de les regrouper.
SÉLECTIONNER.
Les enregistrements doivent être regroupés en utilisant GROUP BY
et MAX()
pour obtenir l'ID maximum pour chaque asker
.
SELECT asker, MAX(ID) ID
FROM TableName
GROUP BY asker
SORTIE
╔════════╦════╗
║ ASKER ║ ID ║
╠════════╬════╣
║ Bob ║ 2 ║
║ Marley ║ 3 ║
╚════════╩════╝
Les autres ont raison d'utiliser MAX (ID) pour obtenir les résultats souhaités. Si vous vous demandez pourquoi votre requête ne fonctionne pas, c'est parce que ORDER BY
survient après le GROUP BY
.
Pour obtenir chaque colonne:
SELECT * FROM questions
WHERE id IN
(SELECT max(id) as id, asker
FROM questions
GROUP by asker
ORDER by id DESC)
Version améliorée de la réponse de @bluefeet.