Per la tabella corrente di 1,700
righe la soluzione è OK.
Se si dispone dello 100,000
di righe, lo DISTINCT
potrebbe diventare inefficiente.
Ecco l'articolo nel mio blog che mostra come farlo in modo efficiente:
Questa soluzione impiega un indice su name
. Salterà sopra i tasti indice, selezionando ogni prima lettera al massimo una volta.
In primo luogo, è necessario creare una funzione:
CREATE FUNCTION fn_get_next_code(initial INT) RETURNS INT
NOT DETERMINISTIC
READS SQL DATA
BEGIN
DECLARE _next VARCHAR(200);
DECLARE EXIT HANDLER FOR NOT FOUND RETURN NULL;
SELECT ORD(SUBSTRING(name, 1, 1))
INTO _next
FROM t_names
WHERE name >= CHAR(initial + 1)
ORDER BY
name
LIMIT 1;
RETURN _next;
END
Questa funzione, dato un codice di una lettera di partenza, restituisce la prima lettera di partenza vicino alla data dal vostro tavolo.
secondo luogo, utilizzare questa funzione in una query:
SELECT CHAR(@r) AS starting,
@r := fn_get_next_letter(@r) AS next
FROM (
SELECT @r := ORD(LEFT(MIN(name), 1))
) vars, mytable
WHERE @r IS NOT NULL
In ogni iterazione, sessione variabile @r
salterà la lettera successiva partenza utilizzando un indice.
Questo sarà molto veloce, ma si ripaga da solo se si dispone di centinaia di migliaia di righe.
Altrimenti basta usare DISTINCT
.
Quanti dischi hai nel tuo tavolo?Volevo pubblicare una versione ottimizzata ma non so se disturbare :) – Quassnoi
OK, l'ho postato comunque :) Probabilmente domani farò un post nel mio blog fuori dalla tua domanda. – Quassnoi