2017-05-30 1 views
0

Ich versuche, eine Abfrage zu optimieren, die einen inneren Join verwendet, und ich bin durch den Unterschied der Leistung zwischen zwei sehr ähnlichen Abfragen verwirrt.Versuchen, den Unterschied des Verhaltens zwischen zwei inneren Join-Abfragen zu verstehen

Ich hoffe, etwas Licht dazu zu bringen.

Die Tabellen sehen wie folgt aus:

Aggregates:

+-recid(key)-+-avg---+ 
+------------+-------+ 

Geschichte:

+-recid(key)-+-value-+ 
+------------+-------+ 

Ziel, für einen bestimmten Schlüssel zu erhalten ist (wir 1234 übernehmen), mittlere und Wert.

Ich habe zwei Abfragen versucht, die mir sehr ähnlich scheinen:

SELECT a.avg, b.value FROM aggregates a, history b 
WHERE a.recid = b.recid 
AND a.recid = 1234 

nimmt 5 Sekunden

Aber

SELECT a.avg, b.value FROM aggregates a, history b 
WHERE a.recid = 1234 
AND b.recid = 1234 

läuft in weniger als einer Sekunde ausgeführt werden.

Diese zwei Abfragen geben das gleiche Ergebnis. Ich mag den großen Unterschied in der Leistung verstehen

+0

Markieren Sie die von Ihnen verwendeten dbms. Verschiedene Produkte optimieren auf unterschiedliche Weise. – jarlh

+1

Übrigens, haben Sie die beiden Abfragen mehrmals in unterschiedlicher Reihenfolge ausgeführt? (Kalt/heiß Daten.) – jarlh

+0

Ja, ich habe es versucht, es ist sehr reproduzierbar, man ist konsequent ~ 5 mal langsamer als die anderen – Maxime

Antwort

0

Zuerst lernen zu verwenden richtigen explizite JOIN Syntax (das Ende des Spiel ein besseres Verständnis, ist eine bessere Leistung für diese Abfrage zu erreichen!):

SELECT a.avg, h.value 
FROM aggregates a JOIN 
    history h 
    ON a.recid = h.recid 
WHERE a.recid = 1234; 

Dies wirkt sich nicht auf die Leistung aus, aber es ist die korrekte, moderne Syntax.

Angenommen, Sie haben Indizes auf aggregates(recid) und history(recid), dann sollten die beiden Versionen sehr ähnliche Ausführungspläne in fast jeder Datenbank haben, die ich mir vorstellen kann. Diese beiden Indizes würden für solche Abfragen empfohlen werden.

Eine Möglichkeit ist kalt gegen warm Cache. Wenn Sie eine Abfrage zum ersten Mal ausführen, müssen die Daten in den Speicher geladen werden. Das kann länger dauern. Für das richtige Timing müssen Sie dies berücksichtigen.

Schließlich, wenn Sie wirklich den Unterschied verstehen wollen, dann müssen Sie den Ausführungsplan betrachten. Die meisten Datenbanken bieten eine einfache Möglichkeit, zu erklären, wie die Abfrage ausgeführt wird.

0

Nicht sicher absolut, aber es könnte sein, dass Ihr zweiter Abfrageausführungsplan bereits zwischengespeichert ist und somit DB-Optimierer nicht benötigt wurde. BTW, Ihre erste Abfrage sollte Änderungen sein, wie unten ANSI Stil JOIN-Syntax zu verwenden

SELECT a.avg, b.value FROM aggregates a 
JOIN history b ON a.recid = b.recid 
WHERE a.recid = 1234 
0

Die zweite Abfrage könnte einen Cross Join dann Filterung der Ergebnisse durchführen werden, obwohl es eine sehr alt sein müsste Version von Oracle, dass dumm zu sein. Aber Sie müssen sich den Abfrageplan ansehen, um es herauszufinden. Wenn sie durchweg unterschiedliche Leistung zeigen, dann garantiere ich, dass die Abfragepläne unterschiedlich sein werden.

Verwandte Themen