Sqlserver
 sql >> Datenbank >  >> RDS >> Sqlserver

Wahl des Operators für den Abfrageoptimierer - verschachtelte Schleifen vs. Hash-Match (oder Merge)

UNBEDINGT. Ein Hash-Match wäre eine enorme Verbesserung. Das Erstellen des Hashs auf der kleineren Tabelle mit 19.223 Zeilen und das anschließende Prüfen mit der größeren Tabelle mit 65.991 Zeilen ist eine viel kleinere Operation als die verschachtelte Schleife, die 1.268.544.993 Zeilenvergleiche erfordert.

Der einzige Grund, warum der Server die verschachtelten Schleifen wählen würde, ist, dass er die Anzahl der beteiligten Zeilen stark unterschätzt hat. Verfügen Ihre Tabellen über Statistiken, und wenn ja, werden sie regelmäßig aktualisiert? Statistiken ermöglichen es dem Server, gute Ausführungspläne auszuwählen.

Wenn Sie Statistiken richtig adressiert haben und immer noch ein Problem haben, können Sie sie zwingen, einen HASH-Join wie folgt zu verwenden:

SELECT *
FROM
   TableA A -- The smaller table
   LEFT HASH JOIN TableB B -- the larger table

Bitte beachten Sie, dass in dem Moment, in dem Sie dies tun, auch die Join-Reihenfolge erzwungen wird. Das bedeutet, dass Sie alle Ihre Tabellen richtig anordnen müssen, damit ihre Join-Reihenfolge sinnvoll ist. Im Allgemeinen würden Sie den Ausführungsplan untersuchen, über den der Server bereits verfügt, und die Reihenfolge Ihrer Tabellen in der Abfrage entsprechend ändern. Wenn Sie damit nicht vertraut sind, die Grundlagen sind, dass jeder "linke" Eingang zuerst kommt, und in grafischen Ausführungsplänen ist der linke Eingang der untere eines. Bei einer komplexen Verknüpfung mit vielen Tabellen müssen möglicherweise Verknüpfungen in Klammern gruppiert oder RIGHT JOIN verwendet werden um den Ausführungsplan optimal zu gestalten (linke und rechte Eingaben vertauschen, aber die Tabelle an der richtigen Stelle in der Join-Reihenfolge einführen).

Im Allgemeinen ist es am besten, die Verwendung von Join-Hinweisen und das Erzwingen der Join-Reihenfolge zu vermeiden, also tun Sie zuerst, was immer Sie können! Sie könnten sich die Indizes der Tabellen ansehen, Fragmentierung, Spaltengrößen reduzieren (z. B. mit varchar statt nvarchar wo Unicode nicht erforderlich ist) oder die Abfrage in Teile aufteilen (zuerst in eine temporäre Tabelle einfügen, dann mit dieser verbinden).