2009-08-20 10 views
5

Date un'occhiata alla tabella di MySQL seguito chiamati "articoli":trovare la riga con il valore massimo di id in MySQL

+----+-----------+---------+------------------------+--------------------------+ 
| id | articleId | version | title     | content     | 
+----+-----------+---------+------------------------+--------------------------+ 
| 1 |   1 | 0.0  | ArticleNo.1 title v0.0 | ArticleNo.1 content v0.0 | 
| 2 |   1 | 1.0  | ArticleNo.1 title v1.0 | ArticleNo.1 content v1.0 | 
| 3 |   1 | 1.5  | ArticleNo.1 title v1.5 | ArticleNo.1 content v1.5 | 
| 4 |   1 | 2.0  | ArticleNo.1 title v2.0 | ArticleNo.1 content v2.0 | 
| 5 |   2 | 1.0  | ArticleNo.2 title v1.0 | ArticleNo.2 content v1.0 | 
| 6 |   2 | 2.0  | ArticleNo.2 title v2.0 | ArticleNo.2 content v2.0 | 
+----+-----------+---------+------------------------+--------------------------+ 

Nel tentativo di trovare una query per restituire Articles.id dove Articles.version è il numero massimo

La tabella Articoli effettiva contiene oltre 10.000 voci.

Quindi, in questo esempio, desidero che vengano restituiti Articles.id 4 e 6. Ho visto parole chiave distinte e funzione max() ma non riesco a inchiodarlo.

Eventuali suggerimenti apprezzato ...

risposta

4

Hai bisogno di un domanda secondaria qui:

SELECT a.id, a.version 
FROM articles a 
WHERE a.version = (
    SELECT MAX(version) 
    FROM articles b 
    WHERE b.articleId = a.articleId 
) 
+0

Restituisce solo tutte le ultime versioni degli articoli, scartando le versioni precedenti/precedenti. Grazie mille ragazzi grazie mille! –

+0

Solo per la cronaca: T.J. Crowder ha sottolineato nella sua risposta che una sub-query non è obbligatoria: può essere eseguita anche con un SINISTRO SINISTRO. – soulmerge

4

È possibile utilizzare un subquery qui:

select 
    a.id 
from 
    articles a 
where 
    a.version = (select max(version) from articles) 

Poiché questo non è una subquery correlata, sarà abbastanza veloce (più veloce o più veloce di un join), quindi non devi preoccuparti di questo. Ma restituirà tutti i valori che hanno il massimo articleid.

Ovviamente, ti consiglio di lanciare un indice su articleid (supponendo che lo id sia già in cluster). Questo lo aiuterà a tornare ancora più velocemente.

Come notato nei commenti, se si desidera ottenere la versione massima per ogni articleid, è possibile effettuare le seguenti operazioni:

select 
    a.id 
from 
    articles a 
    inner join (select articleid, max(version) 
       from articles group by articleid) as b on 
     a.articleid = b.articleid 
     and a.version = b.version 

questo creerà un join da quella subquery e in genere molto più veloce di una sottoquery correlata che seleziona il massimo per ogni articleid.

+1

Questo non è giusto - questo seleziona l'ID articolo massimo è max, non la versione articolo. – tw39124

+0

@ Tom: Sì, e ora l'ho risolto, quindi è giusto. – Eric

+0

Si noti che questo selezionerà solo gli articoli che hanno la * stessa * versione. Se vuoi recuperare l'ultima versione di * ogni * articolo, dai un'occhiata alla mia risposta qui sotto. – soulmerge

1

SELECT Articles.id FROM Articles WHERE Articles.version IN (SELECT MAX(Articles.version) FROM Articles)

1

forse qualcosa di simile:

select * from articoli in cui articleId in (select max (articleversion) da articoli)

1

Si può fare

SELECT articles.id 
    FROM articles a 
WHERE NOT EXISTS(SELECT * FROM articles a2 WHERE a2.version > a.version) 

I don' So che MySQL si esibirà con esso, ma Oracle e SQL Server stanno bene con esso.

5

Dal MySQL manual, questo fa il trucco:

SELECT a1.id 
FROM Articles a1 
LEFT JOIN Articles a2 ON a1.articleId = a2.articleId AND a1.version < a2.version 
WHERE a2.articleId IS NULL; 

si veda il link per logica.

+0

Sappi anche che le sottoquery nella clausola WHERE in MySQL possono essere eseguite per ogni riga del risultato, quindi questa è probabilmente la risposta migliore. –

1

Tutte le risposte di cui sopra possono risolvere il problema dichiarato di DJDonaL3000. Ma la maggior parte di esse è una sottoquery correlata che ostacola le prestazioni dell'applicazione. Se si utilizza un'applicazione cloud, suggerisco di non utilizzare le query sopra. Il modo migliore è quindi di mantenere due tabelle, A e B. A contenenti sempre l'ultima versione dell'articolo e B con i dettagli di tutte le versioni. Il problema è che ci saranno più aggiornamenti e inserimenti nelle tabelle, ma il recupero sarà più veloce in quanto è sufficiente eseguire una query di selezione normale nella tabella A.Fare gruppo per e max in una query interna ti costerà

Problemi correlati