Z tego postu Jak używać ROW_NUMBER w następującej procedurze?
Istnieją dwie wersje odpowiedzi, w których jedna używa a, sub-query
a druga używa a, CTE
aby rozwiązać ten sam problem.
A zatem, jaka jest zaleta używania zapytania CTE (Common Table Expression)
nad „pod-zapytaniem” (a zatem bardziej czytelne, co faktycznie robi zapytanie)
Jedyną zaletą korzystania z CTE
over sub-select
jest to, że rzeczywiście mogę nazwaćsub-query
. Czy istnieją inne różnice między tymi dwoma, gdy CTE jest używane jako proste (nierekursywne) CTE?
sql
sql-server
tsql
subquery
common-table-expression
dance2die
źródło
źródło
Odpowiedzi:
W wersji z zapytaniem podrzędnym i prostym (nierekurencyjnym) CTE są one prawdopodobnie bardzo podobne. Musiałbyś użyć programu profilującego i aktualnego planu wykonania, aby wykryć wszelkie różnice, a to byłoby specyficzne dla twojej konfiguracji (więc nie możemy podać pełnej odpowiedzi).
W ogóle ; CTE może być używane rekurencyjnie; zapytanie podrzędne nie może. Dzięki temu szczególnie dobrze nadają się do konstrukcji drzewiastych.
źródło
A CTE can be used recursively; a sub-query cannot
. Przykład byłby świetny.Główną zaletą wyrażenia Common Table Expression (kiedy nie używasz go do zapytań rekurencyjnych ) jest hermetyzacja, zamiast deklarowania zapytania podrzędnego w każdym miejscu, w którym chcesz go użyć, możesz je zdefiniować raz, ale masz wiele odniesień do tego.
Jednak ten sposób nie oznacza, że jest on wykonywany tylko raz (jak w poprzednich iteracjach tym samym odpowiedź , dziękuję wszystkim osobom, które komentuje). Zapytanie z pewnością ma potencjał do wielokrotnego wykonania, jeśli odwołuje się do niego wiele razy; optymalizator zapytań ostatecznie podejmuje decyzję, jak należy interpretować CTE.
źródło
CTE
są najbardziej przydatne do rekurencji:zwróci
@n
wiersze (do101
). Przydatne do kalendarzy, fikcyjnych zestawów wierszy itp.Są też bardziej czytelne (moim zdaniem).
Poza tym są
CTE
isubqueries
są identyczne.źródło
;WITH blabla AS ...)
WITH
,MERGE
i podobnieJedyną różnicą, o której nie wspomniano, jest odniesienie do pojedynczego CTE w kilku częściach związku
źródło
O ile czegoś nie brakuje, równie łatwo możesz nazwać CTE i podzapytania.
Myślę, że główną różnicą jest czytelność (uważam, że CTE jest bardziej czytelne, ponieważ definiuje podzapytanie z góry, a nie pośrodku).
A jeśli chcesz coś zrobić z rekurencją, będziesz miał trochę problemów z zrobieniem tego z podzapytaniem;)
źródło
Ważnym faktem, o którym nikt nie wspomniał, jest to, że (przynajmniej w postgres) CTE to ogrodzenia optymalizacyjne:
https://blog.2ndquadrant.com/postgresql-ctes-are-optimization-fences/
Oznacza to, że będą traktowane jako własne zapytania niepodzielne, a nie dołączone do całego planu zapytania. Brakuje mi wiedzy pozwalającej na lepsze wyjaśnienie, ale powinieneś sprawdzić semantykę używanej wersji sql; dla zaawansowanych użytkowników możliwość tworzenia ogrodzenia optymalizacyjnego może zwiększyć wydajność, jeśli jesteś ekspertem w kontrolowaniu planowania zapytań; Jednak w 99% przypadków należy unikać prób mówienia planistowi zapytań, co ma robić, ponieważ to, co myślisz, że będzie szybsze, jest prawdopodobnie gorsze niż to, co według niego będzie szybsze. :-)
źródło
Dodając do odpowiedzi innych osób, jeśli jedno i to samo podzapytanie zostało użyte kilka razy, możesz zastąpić wszystkie te podzapytania jednym CTE. Pozwala to na lepsze ponowne wykorzystanie kodu.
źródło
Jedną rzeczą, którą musisz zrozumieć, jest to, że w starszych wersjach SQL Server (tak, wiele osób nadal musi obsługiwać bazy danych SQL Server 2000), CTE nie są dozwolone, a wtedy tabela pochodna jest najlepszym rozwiązaniem.
źródło
WSKAZÓWKA: (MAXRECURSION n)
Na przykład możesz spróbować:
źródło