2013-06-14 2 views
9

ich mysql nur finden kann Datetime-Abfrage wie:mysql Datetime-Feld mit dem Index eine Reihe ‚wie‘ vs. bekommen "zwischen und Leistung

like '2013-06-12%' 

Ich denke, es den Index nicht nutzen kann. Ich google es, aber kann solches Thema nicht direkt finden. Also habe ich einen Test mit einer Tabelle mit 3308614 Datensätze. Das erste SQL:

Alles, was wir wissen, dieses SQL kann den Index nicht verwenden und es dauert 4 Sekunden, um das Ergebnis zu erhalten. Die zweite SQL:

SELECT * FROM subscription t WHERE t.active_time LIKE '2013-06-30%'; 

Ich weiß nicht, ob es den Index verwenden, aber es dauert 4 Sekunden zu. Die dritte SQL:

SELECT * FROM subscription t WHERE t.active_time > '2007-11-30' AND t.active_time < '2007-12-01'; 

Alle wissen, dass wir das dritte SQL den Index verwenden können, und es dauert 0,016 Sekunden.

Also ich denke, "wie" kann den Index nicht verwenden, wenn Sie das datetime-Feld abfragen, weil mysql datetime Feld in Zeichenfolge zuerst konvertieren und die Zeichenfolge an ähnliche Befehl senden sollte. Ist das korrekt?

+0

"Ist das korrekt?" --- yep – zerkms

+0

Sie können Datum abfragen und wie dieses 't.active_time = '2013-06-30'' – Justin

+0

kann nicht verwenden t.active_time =' 2013-06-30 '!! – bluearrow

Antwort

13

Unter der Annahme, dass t.active_time ‚s Typ DATETIME,

ist

Die folgende Abfrage keinen Index wegen des Funktionsaufrufes verwenden kann. Alle active_time müssen sofort in einen DATE Wert vor dem Vergleich mit '2013-06-30' konvertiert werden. Diese Zeichenfolge wird an erster Stelle in einen DATE-Wert konvertiert, und dies geschieht nur einmal am Anfang der Abfrage.

SELECT * FROM subscription t WHERE DATE(t.active_time) = '2013-06-30'; 

Die zweite Abfrage kann aus ähnlichen Gründen keinen Index verwenden. Sie machen tatsächlich einen String-Vergleich (wegen des Operators LIKE). Alle active_time Werte werden während der Übertragung in eine Zeichenfolge konvertiert.

SELECT * FROM subscription t WHERE t.active_time LIKE '2013-06-30%'; 

Nur der letzte kann einen Index verwenden. Die Strings '2007-11-30' und '2007-12-01' werden in diesem Fall auf gewandelt, weil die < und > Operatoren dies erlauben.

SELECT * FROM subscription t WHERE t.active_time > '2007-11-30' AND t.active_time < '2007-12-01'; 

Letzteres gilt auch für die = und BETWEEN Betreiber.

Zur Information, alle Typen können mit einer Zeichenfolge mit dem Operator LIKE verglichen werden, der wegen der impliziten Konvertierung, die es erfordert, das gleiche Problem wie oben beschrieben ist.

t.active_time = '2013-06-30' funktioniert nicht wie erwartet, da '2013-06-30' zu einem DATETIME Wert umgewandelt wird, das heißt '2013-06-30 00:00:00' sagen.

1

Eine Alternative für solche Fälle ist so etwas wie dies zu tun:

SELECT * 
FROM subscription t 
WHERE t.active_time BETWEEN '2013-06-30 00:00:00' AND '2013-06-30 23:59:59'; 

Am Ende Sie alle Ereignisse von diesem Tag.

Verwandte Themen