Kiedy piszę takie zapytanie ...
select *
from table1 t1
join table2 t2
on t1.id = t2.id
Czy optymalizator SQL, nie będąc pewnym, czy jest to poprawny termin, tłumaczy to na ...
select *
from table1 t1, table2 t2
where t1.id = t2.id
Zasadniczo, czy instrukcja Join w SQL Server jest po prostu łatwiejszym sposobem pisania SQL? Czy jest faktycznie używany w czasie wykonywania?
Edycja: Prawie zawsze i prawie zawsze będę używać składni Join. Jestem po prostu ciekawa, co się dzieje.
sql-server
t-sql
join
optimization
Pan Ant
źródło
źródło
GROUP BY ALL
wGROUP BY ALL
celowo używa ? :-)Odpowiedzi:
Te upadają wewnętrznie na to samo. Ten pierwszy to ten, który zawsze powinieneś pisać . Co ważniejsze, dlaczego to ma znaczenie? Są identyczne pod względem planu wykonania i wydajności (przy założeniu, że nie zepsujesz tego, co łatwiej zrobić z leniwą składnią w starym stylu).
Oto dowód za pomocą AdventureWorks, że nie ma
CROSS JOIN
i niefilter
trwa dalej.Wyraźne dołączenie:
Ukryte połączenie:
Spójrz, mamo! Identyczne plany, identyczne wyniki, nigdzie nie widać połączeń krzyżowych ani filtrów.
(Dla jasności ostrzeżenie dla
SELECT
operatora w obu przypadkach jest niejawną konwersją wpływającą na liczność, w żadnym przypadku nie ma nic wspólnego ze złączeniem.)źródło
Ściśle mówiąc, istnieją dwie różnice w danych wejściowych do optymalizatora zapytań między dwiema formami:
Jak widać
ON
predykat klauzuli jest ściśle związany z łączeniem przy użyciu nowoczesnej składni. Przy starszej składni istnieje logiczne połączenie krzyżowe, po którym następuje relacyjny wybór (filtr wierszy).Optymalizator zapytań prawie zawsze zwija relacyjną selekcję do złączenia podczas optymalizacji, co oznacza, że te dwie formy prawdopodobnie zapewnią równoważne plany zapytań, ale nie ma rzeczywistej gwarancji.
źródło
W przypadku łączenia wewnętrznego są one wymienne, ale w przypadku połączeń zewnętrznych mają różne znaczenia - ON jest zgodny, a GDZIE to proste filtrowanie. Lepiej więc trzymać się właściwego dopasowania składni JOIN w ON.
źródło
OK, byłem ciekawy, więc zrobiłem test. Mam rzeczywiste plany wykonania dla następujących.
i
Porównałem je obiekt po obiekcie i były identyczne. Przynajmniej dla bardzo prostego przykładu, wyszli na to samo. Sprawdziłem także statystyki IO i czas, a były one wystarczająco blisko, aby być tym samym.
To powiedziawszy, powinieneś użyć
JOIN
składni, ponieważ jest łatwiejsza do odczytania i rzadziej popełniasz błędy, szczególnie w skomplikowanych zapytaniach. A składnia*=
/=*
dlaOUTER
złączeń została już usunięta od SQL-Server 2005.źródło