MIN / MAX vs ORDER BY e LIMIT


100

Tra le seguenti domande, quale metodo considereresti il ​​migliore? Quali sono le tue ragioni (efficienza del codice, migliore manutenibilità, meno WTFery) ...

SELECT MIN(`field`)
FROM `tbl`;

SELECT `field`
FROM `tbl`
ORDER BY `field`
LIMIT 1;

Risposte:


126

Nel peggiore dei casi, in cui stai guardando un campo non indicizzato, l'utilizzo MIN()richiede un singolo passaggio completo della tabella. Utilizzando SORTe LIMITrichiede un filesort. Se eseguito contro un tavolo di grandi dimensioni, ci sarebbe probabilmente una differenza significativa nelle prestazioni percepite. Come punto dati senza senso, ha MIN()preso .36s mentre SORTe LIMIT.84s contro una tabella di 106.000 righe sul mio server di sviluppo.

Se, tuttavia, stai guardando una colonna indicizzata, la differenza è più difficile da notare (il punto dati senza significato è 0,00 s in entrambi i casi). Guardando l'output di spiegare, tuttavia, sembra che MIN()sia in grado di estrarre semplicemente il valore più piccolo dall'indice (righe 'Seleziona tabelle ottimizzate' e 'NULL') mentre SORTe LIMITdeve ancora eseguire un attraversamento ordinato dell'indice (106.000 righe). L'effettivo impatto sulle prestazioni è probabilmente trascurabile.

Sembra che MIN()sia la strada da percorrere: è più veloce nel peggiore dei casi, indistinguibile nel migliore dei casi, è l'SQL standard ed esprime più chiaramente il valore che stai cercando di ottenere. L'unico caso in cui sembra che l'uso di SORTe LIMITsarebbe auspicabile sarebbe, come menzionato da mson , in cui stai scrivendo un'operazione generale che trova i valori N superiori o inferiori da colonne arbitrarie e non vale la pena scrivere l'operazione per casi speciali.


7
o (n) per un singolo passaggio vs 0 (nlogn) per lo smistamento
Abhishek Iyer

1
@AbhishekIyer hai perfettamente ragione, ma aggiungerei "nel peggiore dei casi per campo non indicizzato".
dmikam

Quella parte sul peggior caso non indicizzato è sbagliata. Hai sempre bisogno di una scansione completa, in quale altro modo sai che è un minimo o un massimo? Non è che tu stia scansionando e il valore urla: "Ehi, finalmente mi hai trovato! Sono Jack, il massimo!".
Robo Robok,

In un test con una tabella indicizzata con 470 milioni di righe, entrambe le query richiedono 0,00 s. Tuttavia, se aggiungiamo alle query un filtro "WHERE field2 = x", la query con LIMIT richiede ancora 0,00 se la query con MIN richiede 0,21 s.
Antonio Cañas Vargas

12
SELECT MIN(`field`)
FROM `tbl`;

Semplicemente perché è ANSI compatibile. Il limite 1 è specifico per MySql come TOP è per SQL Server.


La maggior parte dei DBMS ha limite / offset o equivalente, ed è utilizzato nella maggior parte delle app su cui ho lavorato (non come alternativa a MIN, ma per altri scopi come l'impaginazione.)
finnw

@finnw - Sono d'accordo, ma l'esempio dell'interrogante stava confrontando esplicitamente limit con min.
Otávio Décio

9

Come hanno sottolineato mson e Sean McSomething , MIN è preferibile.

Un altro motivo per cui ORDER BY + LIMIT è utile è se si desidera ottenere il valore di una colonna diversa dalla colonna MIN.

Esempio:

SELECT some_other_field, field
FROM tbl
ORDER BY field
LIMIT 1

4

Penso che le risposte dipendono da quello che stai facendo.

Se hai una query 1 off e l'intento è semplice come specificato, è preferibile selezionare min (campo).

Tuttavia, è comune che questi tipi di requisiti cambino in: prendi i primi n risultati, prendi n-esimo risultato, ecc.

Non penso che sia un'idea troppo terribile da affidare al database scelto. Cambiare dbs non dovrebbe essere fatto alla leggera e devi rivedere il prezzo che paghi quando fai questa mossa.

Perché limitarti ora, per il dolore che potresti o non potresti provare in seguito?

Penso che sia positivo rimanere ANSI il più possibile, ma questa è solo una linea guida ...


3

Date prestazioni accettabili, userei il primo perché è semanticamente più vicino all'intento.
Se le prestazioni fossero un problema, (la maggior parte degli ottimizzatori moderni probabilmente ottimizzerà entrambi per lo stesso piano di query, anche se è necessario testare per verificarlo), allora ovviamente utilizzerei quello più veloce.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.