Es gibt Situationen, in denen eine sehr große Abfrage erforderlich ist, die mehrere Tabellen mit Sub-Select-Anweisungen verknüpft, um die gewünschten Ergebnisse zu erzielen.
Meine Frage ist, sollten wir in Betracht ziehen, mehrere kleinere Abfragen zu verwenden und die logischen Operationen in die Anwendungsschicht zu bringen, indem wir die Datenbank in mehr als einem Aufruf abfragen, oder es ist besser, sie alle auf einmal zu haben?
Betrachten Sie zum Beispiel die folgende Abfrage:
SELECT *
FROM `users`
WHERE `user_id` IN (SELECT f2.`friend_user_id`
FROM `friends` AS f1
INNER JOIN `friends` AS f2
ON f1.`friend_user_id` = f2.`user_id`
WHERE f2.`is_page` = 0
AND f1.`user_id` = "%1$d"
AND f2.`friend_user_id` != "%1$d"
AND f2.`friend_user_id` NOT IN (SELECT `friend_user_id`
FROM `friends`
WHERE `user_id` = "%1$d"))
AND `user_id` NOT IN (SELECT `user_id`
FROM `friend_requests`
WHERE `friend_user_id` = "%1$d")
AND `user_image` IS NOT NULL
ORDER BY RAND()
LIMIT %2$d
Wie geht das am besten?
quelle
Als jemand, der diese großen und komplizierten Abfragen unterstützen / bereinigen muss, würde ich sagen, dass es weitaus besser ist, sie in mehrere kleine, leicht verständliche Abschnitte aufzuteilen. Unter Performance-Gesichtspunkten ist es nicht unbedingt besser, aber Sie geben SQL zumindest eine bessere Chance, einen guten Abfrageplan zu entwickeln.
Erleichtern Sie den Menschen, die Ihnen folgen, das Leben, und sie werden gute Dinge über Sie sagen. Machen Sie es ihnen schwer und sie werden Sie verfluchen.
quelle
Meine 2 Cent für die 2 Schlüsselwörter Abfrage-Performance und Skalierbarkeit:
Abfrageleistung: Die SQL Server-Parallelität funktioniert bereits sehr gut, wenn Abfragen in Suchanfragen mit mehreren Threads unterteilt werden. Daher bin ich mir nicht sicher, wie stark sich die Abfrageleistung bei SQL Server verbessert. Sie müssen sich den Ausführungsplan ansehen, um festzustellen, wie viel Parallelität Sie erhalten, wenn Sie ihn ausführen, und die Ergebnisse in beide Richtungen vergleichen. Wenn Sie am Ende einen Abfragehinweis verwenden müssen, um die gleiche oder eine bessere Leistung zu erzielen, lohnt sich IMO nicht, da der Abfragehinweis später möglicherweise nicht optimal ist.
Skalierbarkeit: Das Lesen der Abfragen ist möglicherweise einfacher, wie von datagod angegeben, und das Aufteilen in separate Abfragen ist sinnvoll, wenn Sie Ihre neuen Abfragen auch in anderen Bereichen verwenden können, sie aber nicht auch für andere Anrufe verwenden möchten Es sind noch mehr gespeicherte Prozesse für eine Aufgabe zu verwalten, und IMO würde keinen Beitrag zur Skalierbarkeit leisten.
quelle
LIMIT
Manchmal bleibt keine andere Wahl, als die große / komplexe Abfrage in kleine Abfragen aufzuteilen. Der beste Weg, dies festzustellen, wäre,
EXPLAIN
Anweisung mit derSELECT
Anweisung zu verwenden. Die Anzahl der Traces / Scans, die Ihre Datenbank zum Abrufen Ihrer Daten durchführen wird, ist das Produkt der von IhrerEXPLAIN
Abfrage zurückgegebenen "Zeilen" -Werte . In unserem Fall hatten wir eine Abfrage, die 10 Tabellen verknüpft. Insbesondere betrug der Trace 409 Millionen, die unsere Datenbank bloggten und die CPU-Auslastung unseres DB-Servers um mehr als 300% erhöhten. Wir konnten dieselben Informationen abrufen, indem wir die Abfragen viel schneller aufteilten.Kurz gesagt, in einigen Fällen ist das Aufteilen einer komplexen / großen Abfrage sinnvoll, in anderen Fällen kann es jedoch zu zahlreichen Leistungs- oder Wartungsproblemen kommen. Dies sollte von Fall zu Fall behandelt werden.
quelle