sql >> Databáze >  >> RDS >> Sqlserver

Přepište Query Optimizer pro vaše spojení T-SQL pomocí FORCEPLAN

SET FORCEPLAN příkaz přepíše logiku používanou optimalizátorem dotazů SQL Server ke zpracování T-SQL SELECT prohlášení.

Přesněji řečeno, když FORCEPLAN je nastaveno na ON , optimalizátor dotazů zpracuje spojení ve stejném pořadí, v jakém jsou tabulky uvedeny v FROM klauzule dotazu.

To také vynutí použití spojení vnořených smyček, pokud nejsou vyžadovány jiné typy spojení k vytvoření plánu pro dotaz nebo pokud nejsou požadovány pomocí tipů na spojení nebo tipů na dotaz.

Příklad

Ukázat, jak FORCEPLAN funguje, spustím dva SELECT dotazy, nejprve pomocí FORCEPLAN nastavte na ON a poté pomocí FORCEPLAN nastavte na OFF .

Oba dotazy jsou identické, s výjimkou toho, že tabulky spojení jsou uvedeny v jiném pořadí.

V tomto příkladu používám SHOWPLAN_XML k zobrazení odhadovaného plánu dotazů, ale stejně snadno můžete použít jinou metodu (například tlačítko Vysvětlit v Azure Data Studio nebo Include Actual Execution Plan ikona v SSMS pro zobrazení skutečného plánu dotazů).

NASTAVIT FORCEPLAN ZAPNUTO

SET FORCEPLAN ON;
GO

SET SHOWPLAN_XML ON;
GO

SELECT
    ar.ArtistName,
    al.AlbumName,
    g.Genre
FROM 
    Artists ar 
    INNER JOIN Albums al 
    ON ar.ArtistId = al.ArtistId 
    INNER JOIN Genres g 
    ON al.GenreId = g.GenreId;

SELECT
    ar.ArtistName,
    al.AlbumName,
    g.Genre
FROM 
    Albums al
    INNER JOIN Genres g 
    ON al.GenreId = g.GenreId
    INNER JOIN Artists ar 
    ON ar.ArtistId = al.ArtistId;

Výsledek:

Vidíme, že plán dotazů pro každý dotaz odráží pořadí, ve kterém jsem zahrnul názvy tabulek do FROM doložka.

VYPNĚTE FORCEPLAN

SET SHOWPLAN_XML OFF;
GO

SET FORCEPLAN OFF;
GO

SET SHOWPLAN_XML ON;
GO

SELECT
    ar.ArtistName,
    al.AlbumName,
    g.Genre
FROM 
    Artists ar 
    INNER JOIN Albums al 
    ON ar.ArtistId = al.ArtistId 
    INNER JOIN Genres g 
    ON al.GenreId = g.GenreId;

SELECT
    ar.ArtistName,
    al.AlbumName,
    g.Genre
FROM 
    Albums al
    INNER JOIN Genres g 
    ON al.GenreId = g.GenreId
    INNER JOIN Artists ar 
    ON ar.ArtistId = al.ArtistId;

Výsledek:

Tentokrát mají oba dotazy za následek identický plán dotazů. Optimalizátor dotazů ignoroval pořadí, ve kterém jsem je uvedl v FROM klauzule a určila si vlastní pořadí.

Všimněte si, že FORCEPLAN nastavení nemění data vrácená SELECT prohlášení. Skutečné výsledky jsou stejné bez ohledu na to, zda FORCEPLAN je nastaveno na ON nebo OFF . Jediný rozdíl je ve způsobu zpracování tabulek (což by mohlo mít vliv na výkon).

Můžete použít SET FORCEPLAN ve spojení s radami optimalizátoru dotazů k dalšímu ovlivnění způsobu zpracování dotazu.


  1. Tipy pro opravu fragmentace indexu SQL Server

  2. HikariCP - připojení není k dispozici

  3. Proč PostgreSQL provádí sekvenční skenování na indexovaném sloupci?

  4. Jak lze vytvořit index v části data pole DATETIME v MySql