2013-10-17 1 views
3

J'ai une table qui a le schéma suivantPourquoi je ne peux pas me débarrasser de filesort dans une requête MySQL que je construis déjà index pour

Id, INT, clé primaire

ID_requête , INT

CreatedTime, index DateTime

et I créés composé (ID_requête, CreatedTim e)

Comment se fait que lorsque je cours expliquer select * from test où ID_requête en (1,6) par ordre CreatedTime desc

Je reçois toujours le suivant qui a le filesort? Toute idée comment pourrais-je supprimer des fichiers? « Utilisation où, utilisant filesort »

Explain result

+0

L'optimiseur de MySQL a déterminé qu'il est plus rapide de trier le fichier que de parcourir l'index _pour cette requête_. Si la requête est différente, ou si le nombre de lignes dans la table est différent, MySQL peut choisir de faire autre chose. Laissez-le faire son travail - c'est presque certainement mieux que vous ou moi. –

Répondre

1

Vous avez pas réellement construit un indice qui peut être utilisé pour cette requête.

Un index ne peut être utilisé que pour les recherches et le tri de la colonne la plus à gauche vers la droite. Dès que quelque chose de non-utile est rencontré, le reste de l'index est ignoré.

Vous ne publiez pas la sortie de votre EXPLAIN mais je pense que si l'indice est en cours d'examen et ID_requête est un INT, que vous trouverez Key_len = 4 sens que seuls les 4 octets les plus à gauche (ID_requête) sont utiles à l'optimiseur.

Un index sur (QueryId, CreatedTime) pour extraire les enregistrements par QueryId et les trier par CreatedTime si et seulement si vous sélectionnez une valeur unique pour QueryId. Lorsque vous faites cela, l'index retournera les lignes correspondant à ce QueryId, déjà trié par CreatedTime, et l'optimiseur s'en rend compte.

À l'inverse, si vous recherchez plusieurs valeurs de ID_requête, les lignes retournées par l'index sont retournées triées par ID_requête et puis par CreatedTime au sein de chaque groupe de ID_requête ... de sorte que le plus filesort est nécessaire parce que les valeurs de CreatedTime sont essentiellement triés dans aucun ordre utile. Si vous ORDER BY QueryId, CreatedTime, le fichier doit disparaître, bien sûr, mais ce n'est probablement pas ce que vous voulez. Un index sur (CreatedTime, QueryId) n'aidera pas non plus, parce que l'ID de requête n'est pas à gauche, et à moins qu'il y ait un très petit nombre de lignes, le serveur pourrait tirer les lignes pré-triées par CreatedTime , mais il devrait analyser toutes les lignes pour trouver des valeurs correspondantes pour QueryId.

En résumé, vous ne pouvez pas entièrement index pour une requête comme celle-ci, et Using filesort n'est pas quelque chose qui peut toujours être évitée.

+0

Salut Michael, j'ai ajouté l'image du résultat de l'explication à la question originale, s'il vous plaît jeter un oeil.J'ai trouvé plusieurs endroits en ligne qui ont la même situation que moi et ils ont utilisé la même manière que moi et prétendu prendre effet – user2490226

Questions connexes