Domanda

Ho una tabella come questo

CREATE TABLE IF NOT EXISTS `tbl_folder` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `owner_userid` int(11) NOT NULL,
  `name` varchar(63) NOT NULL,
  `description` text NOT NULL,
  `visibility` tinyint(4) NOT NULL DEFAULT '2',
  `num_items` int(11) NOT NULL DEFAULT '0',
  `num_subscribers` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`id`),
  KEY `owner_userid` (`owner_userid`),
  KEY `vis_sub_item` (`visibility`,`num_subscribers`,`num_items`)
) ENGINE=InnoDB

dal momento che ho un indice sulla visibilità, NUM_SUBSCRIBERS e NUM_ITEMS, mi aspetto che solo le prime 15 righe devono solo essere guardato, invece, SPIEGARE dice 55856 righe. Qualche idea? Grazie

EXPLAIN SELECT t.id, name, description, owner_userid, num_items, num_subscribers
FROM  `tbl_folder`  `t` 
WHERE visibility =2
ORDER BY  `t`.`num_subscribers` DESC ,  `t`.`num_items` DESC 
LIMIT 15

id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE t ref vis_sub_item vis_sub_item 1 const 55856 Using where
È stato utile?

Soluzione

Il tuo indice 3 campo sembra buona e il EXPLAIN è promettente.

Anche se si dice "55856 righe", che è solo un stima fornito da EXPLAIN.

Dal key_len =1, si sa che sta utilizzando il primo byte del tuo indice composto come uguaglianza / di riferimento.

Dal momento che non v'è alcun filesort menzionato nel vostro campo Extra, si sa che il ORDER BY / smistamento è affidate dall'indice.

Se si controlla le statistiche handler_% sessione, si avrà una migliore idea di quante righe sono in realtà essere di lettura.

Pensieri collaterali:

Dal momento che sai che stai in ultima analisi, andando a colpire su disco per recuperare i file, se il 99% dei dati ha visibility=2 (solo speculando), si sarebbe probabilmente ottenere come altrettanto buono / risultati veloci con un indice composto solo su num_subscribers & num_items. O forse come buono / veloce se si ha un unico indice su num_subscribers, a seconda di essa la cardinalità / unicità.

Altri suggerimenti

Non credo che sembra EXPLAIN presso la clausola OFFSET o LIMIT. EXPLAIN dovrebbe indicare in che modo sarebbe stata eseguita la query, che cosa ha usato le chiavi, come le tabelle sono unite, ecc La clausola LIMIT è un po 'come un modificatore di query post ... ora che sappiamo quello che vogliamo, solo dare il em prima così tanti. Così, il campo righe contiene il numero di possibili file che esistono nella query. Da lì, OFFSET e LIMIT avrebbero selezionare quelli specifici che si desidera.

Sto pensando che se si eseguisse il tuo SELECT senza EXPLAIN, si otterrebbe il numero di record che si voleva.

Sì, il problema è che l'indice non è corretto. Voglio dire che indicizzati tutti i 3 campi e la vostra selezione di query controlla solo per uno. In MySQL indicizzazione 2 righe separatamente è diverso da indicizzare 3 righe insieme.

Prova

CREATE TABLE IF NOT EXISTS `tbl_folder` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `owner_userid` int(11) NOT NULL,
  `name` varchar(63) NOT NULL,
  `description` text NOT NULL,
  `visibility` tinyint(4) NOT NULL DEFAULT '2',
  `num_items` int(11) NOT NULL DEFAULT '0',
  `num_subscribers` int(11) NOT NULL DEFAULT '0',
  PRIMARY KEY (`id`),
  KEY `owner_userid` (`owner_userid`),
  KEY `vis_index` (`visibility`),
  KEY `vis_sub_item` (`num_subscribers`,`num_items`)
) ENGINE=InnoDB
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top