2016-03-23 8 views
0

Ich habe diese Abfrage auf einem iOS-App:Abfrageoptimierung oder Pufferung

EXPLAIN QUERY PLAN SELECT 
    m.`id`, m.`no`, m.`name`, m.`image`, m.`stock`, 
    mp.`unit_price_from`, mp.`unit_list_price_from`, mp.`unit_price`, mp.`unit_list_price`, 
    (SELECT COUNT(`color_no`) FROM `variants` WHERE `model_no` = m.`no`) AS `variants_count`, 
    (SELECT COUNT(DISTINCT `color_no`) FROM `variants` WHERE `model_no` = m.`no`) AS `styles_count` 
FROM `models` m 
LEFT JOIN `model_prices` mp ON mp.`model_id` = m.`id` 
WHERE 
    `noos` = 2 OR `noos` = 1 

Auf dem Simulator auf meinem MacBook dies dauert nur zwischen 124ms und 144ms. Ich habe verschiedene INDEXES auf model_no, color_no und den kombinierten Varianten von ihnen ausprobiert, aber sie führten nicht zu schnelleren Abfragen. Auf einem iPad 3 wird es mühsamer, die Abfrage auf 640ms zu verlangsamen. Dies gibt einen kleinen Schluckauf im Gefühl der App, die ich wirklich loswerden möchte.

Die models Tabelle hat bereits einen Index für das noos zu Feld.

Die variants Tabelle enthält 12677 Datensätze.

Die model_prices Tabelle enthält 2792 Datensätze.

Die models Tabelle enthält 2792 Datensätze.

Ich frage mich, ob es eine Möglichkeit gibt, die COUNT-Unterabfragen zu reformieren, um schnellere Ergebnisse in SQLite zu erhalten. Ich benutze nur eine Art manuelles Caching als letzten Ausweg, wollte aber zuerst sehen, ob einige von euch hier einige Optimierungsmöglichkeiten sehen.

Hier ist das Ergebnis ERKLÄREN:

enter image description here

Antwort

1

Für diese Abfrage:

SELECT m.`id`, m.`no`, m.`name`, m.`image`, m.`stock`, 
     mp.`unit_price_from`, mp.`unit_list_price_from`, mp.`unit_price`, mp.`unit_list_price`, 
     (SELECT COUNT(`color_no`) FROM `variants` WHERE `model_no` = m.`no`) AS `variants_count`, 
     (SELECT COUNT(DISTINCT `color_no`) FROM `variants` WHERE `model_no` = m.`no`) AS `styles_count` 
FROM `models` m LEFT JOIN 
    `model_prices` mp 
     ON mp.`model_id` = m.`id` 
WHERE m.`noos` IN (1, 2); 

Die besten Indizes sein sollte: models(noos, id), model_prices(model_id) und variants(model_no, color_no).

+0

Leider gibt es mir keine Ergebnisse unter 120ms :(. Ich versuchte sogar über-INDEXing auch durch Hinzufügen von separaten INDEXe auf die ID, NOOS, Color_no und MODELL_NO Felder. Ist SQLite mit der gleiche Macken wie MySQL, wo die Abfrage Neuformatierung durch Auswahl unterschiedlicher Pläne verschraubt? –

+0

@Allendar ... Sie wollen nicht überindizieren. Sie wollen die Composite (mehrspaltig) Indizes in der Antwort erwähnt. –

+0

Ich weiß Gordon, ich war Ich habe nur die Tatsache als Test angegeben. Ich habe die INDEXe nachträglich zurückgesetzt. Leider verbessert keine der INDEX-Kombinationen die Ausführungszeit. –