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

Proč jsou skalární funkce SQL Serveru pomalejší?

Ve většině případů je nejlepší vyhnout se skalárně hodnotným funkcím, které odkazují na tabulky, protože (jak řekli jiní) jsou to v podstatě černé skříňky, které je třeba spustit jednou pro každý řádek a nelze je optimalizovat modulem plánu dotazů. Proto mají tendenci se škálovat lineárně, i když přidružené tabulky mají indexy.

Možná budete chtít zvážit použití funkce s hodnotou vložené tabulky, protože jsou vyhodnocovány inline s dotazem a lze je optimalizovat. Získáte požadované zapouzdření, ale výkon při vkládání výrazů přímo do příkazu select.

Jako vedlejší efekt toho, že jsou inline, nemohou obsahovat žádný procedurální kód (žádná deklarace @proměnná; set @proměnná =..; return). Mohou však vrátit několik řádků a sloupců.

Své funkce byste mohli přepsat nějak takto:

create function usf_GIS_GET_LAT(
    @City varchar (30),
    @State char (2)
)
returns table
as return (
  select top 1 lat
  from GIS_Location with (nolock) 
  where [State] = @State
    and [City] = @City
);

GO

create function usf_GIS_GET_LON (
    @City varchar (30),
    @State char (2)
)
returns table
as return (
  select top 1 LON
  from GIS_Location with (nolock)
  where [State] = @State
    and [City] = @City
);

Syntaxe pro jejich použití je také trochu odlišná:

select
    Lat.Lat,
    Lon.Lon
from
    Address_Location with (nolock)
    cross apply dbo.usf_GIS_GET_LAT(City,[State]) AS Lat
    cross apply dbo.usf_GIS_GET_LON(City,[State]) AS Lon
WHERE
    ID IN (SELECT TOP 100 ID FROM Address_Location WITH(NOLOCK) ORDER BY ID DESC)


  1. Použití klauzule EXCEPT v PostgreSQL

  2. MySQL Group_Concat() vs T-SQL String_Agg()

  3. Jak funguje SEC_TO_TIME() v MariaDB

  4. Vyberte poslední řádek pro každou skupinu z oracle