165 votes

Comment sélectionner une ligne entière qui a le plus grand ID dans le tableau ?

Comment pourrais-je faire quelque chose comme ça ?

SQL SELECT row FROM table WHERE id=max(id)

264voto

unutbu Points 222216

Vous pourriez utiliser une sous-sélection :

SELECT row 
FROM table 
WHERE id=(
    SELECT max(id) FROM table
    )

Notez que si la valeur de max(id) n'est pas unique, plusieurs lignes sont retournées.

Si vous ne voulez qu'une seule de ces lignes, utilisez la réponse de @MichaelMior,

SELECT row from table ORDER BY id DESC LIMIT 1

7 votes

@AlirezaSoori : Malgré le nom, id est juste une colonne dans un tableau. Il n'y a aucune garantie que les valeurs de la colonne id La colonne doit être unique.

1 votes

@unutbu En supposant que id n'est pas une clé primaire ou unique :) Compte tenu de son nom, il y a de fortes chances qu'elle le soit. Il convient également de noter que, selon le SGBD que vous utilisez, l'approche avec le sous-sélectionneur peut être beaucoup moins efficace.

3 votes

@MichaelMior : id peut être une clé étrangère, auquel cas elle peut ne pas être unique. J'ai fait quelques tests de référence en utilisant set profiling = 1; ...; show profiles et il apparaît que nos solutions ont les mêmes performances en utilisant MySQL. Pour ma gouverne, savez-vous quel SGBD a de moins bonnes performances pour les sous-sélections ?

160voto

Michael Mior Points 13475

Vous pouvez également faire

SELECT row FROM table ORDER BY id DESC LIMIT 1;

Cela permet de trier les lignes par leur ID dans l'ordre décroissant et de retourner la première ligne. Cela revient à renvoyer la ligne dont l'ID est le plus élevé. Cela suppose bien sûr que id est unique parmi toutes les rangées. Sinon, il pourrait y avoir plusieurs lignes avec la valeur maximale de id et vous n'en aurez qu'une.

1 votes

Pour faire spécifiquement ce que l'OP demande, je ferais ceci. Mais les autres réponses fournissent une meilleure éducation sur la structure SQL :)

0 votes

@Dems Comment cela ? Aucune explication n'est donnée sur les autres réponses ? Je suis bien sûr coupable de cela aussi :(

0 votes

Juste que les autres questions corrigent la syntaxe sans remanier la logique. Ainsi, le PO apprend comment énoncer correctement ce code SQL spécifique.

28voto

Russell Shingleton Points 1786
SELECT * 
FROM table 
WHERE id = (SELECT MAX(id) FROM TABLE)

0 votes

@shA.t SELECT entry FROM table WHERE id = MAX(id) ne fonctionnerait pas ? !

0 votes

@shA.t Aussi, ce que j'essaie de faire ressemble à ce qui suit : SELECT entry_time FROM users_unverified WHERE num_id = (SELECT MAX(num_id) FROM users_unverified WHERE account_email = :account_email) où j'ai juste besoin du entry_time de l'entrée la plus récente dans la base de données. Cette déclaration est-elle suffisante ou devrait-elle être : SELECT entry_time FROM users_unverified WHERE num_id = (SELECT MAX(num_id) FROM users_unverified) AND account_email = :account_email

0 votes

Il n'existe pas de signification fiable pour l'entrée la plus récente dans un résultat de requête, vous devez avoir un champ pour l'heure d'insertion, etc. BTW, veuillez poser votre question séparément, j'espère que vous obtiendrez plus d'attention -HTH ;).

17voto

CakeLikeBoss Points 54

Vous ne pouvez pas donner order by parce que order by fait un "full scan" sur une table.

La requête suivante est meilleure :

SELECT * FROM table WHERE id = (SELECT MAX(id) FROM table);

18 votes

ORDER BY ne fera pas un scan complet si vous supposez que id est la clé primaire de la table. (Et si ce n'est pas le cas, son nom est plutôt mal choisi.) Si ce n'est pas le cas, comment voulez-vous que la clé primaire de la table soit utilisée ? MAX(id) pour fonctionner sans un balayage complet de la table ? S'il n'y a pas d'index, il faut quand même vérifier chaque valeur pour trouver le maximum.

0 votes

@CakeLikeBoss j'ai essayé la requête "order by" et votre requête "SELECT * FROM table WHERE id = (SELECT MAX(id) FROM table) ;" sur une table de 114 lignes alors que cette requête a pris exactement 0.0004 sec à chaque fois alors que la deuxième requête a pris de 0.0007 à 0.0010 sec j'ai répété ceci plusieurs fois

2voto

sumit kumar Points 130

Vous pouvez toujours opter pour des fonctions analytiques qui vous donneront plus de contrôle.

select tmp.row from ( select row, rank() over(partition by id order by id desc ) as rnk from table) tmp where tmp.rnk=1

Si vous rencontrez un problème avec la fonction rank(), selon le type de données, vous pouvez choisir entre row_number() et dense_rank().

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X