Jak tworzyć zmaterializowane widoki w SQL Server?

101

Mam zamiar zaprojektować DW i słyszałem o zmaterializowanych widokach. Właściwie chcę utworzyć widok i powinien aktualizować się automatycznie po zmianie tabel podstawowych. Czy ktoś może wyjaśnić na przykładzie zapytania.

Deepak
źródło

Odpowiedzi:

144

Nazywa się je widokami indeksowanymi w SQL Server - przeczytaj te oficjalne dokumenty, aby uzyskać więcej informacji:

Zasadniczo wszystko, co musisz zrobić, to:

  • utworzyć zwykły widok
  • utwórz indeks klastrowy w tym widoku

i jesteś skończony!

Problem polega na tym, że widok musi spełniać wiele ograniczeń i ograniczeń - są one opisane w białej księdze. Jeśli to zrobisz - to wszystko. Widok jest aktualizowany automatycznie, nie wymaga konserwacji.

Dodatkowe zasoby:

marc_s
źródło
Dzięki za odpowiedź. Mam to, czego chcę ... Chciałbym też wiedzieć o indeksach. Chcę wiedzieć, czy istnieje sposób na wygenerowanie schematu gwiaździstego na serwerze SQL, gdy mam już gotową całą strukturę tabeli? Jeśli tak, jak mogę utworzyć dla tego tabelę faktów?
Deepak
4
Ograniczenia dotyczące umieszczania indeksu klastrowego w widoku są rozległe. Na przykład widok nie może odwoływać się do innych widoków i nie może zawierać połączeń zewnętrznych. Tak więc wiele widoków, które wymagają lepszej wydajności, nie może korzystać z tej metody. Wciąż dobra odpowiedź.
Jeff Wilson
2
Jak wspomniano w pokrewnym pytaniu, artykuł na blogu MSDN blogs.msdn.microsoft.com/ssma/2011/06/20/… podkreśla niektóre kluczowe różnice między widokami zmaterializowanymi a widokami indeksowanymi. Najbardziej problematycznym IMHO jest brak możliwości określenia wyzwalaczy odświeżania: widoki indeksowane są aktualizowane za każdym razem, gdy aktualizowane są tabele podstawowe - co osłabia większość korzyści związanych z wydajnością używania widoku zmaterializowanego. Zakazy dotyczące łączeń, agregacji, funkcji okienkowania i podzapytań sprawiają, że widoki indeksowane są prawie bezcelowe, chyba że dane nie zmieniają się często.
Suncat2000
43

Chociaż z czysto inżynierskiego punktu widzenia, widoki indeksowane brzmią jak coś, co każdy mógłby wykorzystać do poprawy wydajności, ale scenariusz w prawdziwym życiu jest zupełnie inny. Nie udało mi się korzystać z widoków indeksowanych tam, gdzie ich najbardziej potrzebuję z powodu zbyt wielu ograniczeń dotyczących tego, co można indeksować, a czego nie.

Jeśli w widokach istnieją połączenia zewnętrzne, nie można ich użyć. Również typowe wyrażenia tabelowe są niedozwolone ... W rzeczywistości, jeśli masz jakiekolwiek uporządkowanie w podselekcjach lub tabelach pochodnych (na przykład z klauzulą ​​partycjonowanie), również nie masz szczęścia.

To pozostawia tylko bardzo proste scenariusze wykorzystania indeksowanych widoków, co moim zdaniem można zoptymalizować, tworząc odpowiednie indeksy na bazowych tabelach.

Będę podekscytowany, słysząc scenariusze z życia, w których ludzie faktycznie używali indeksowanych widoków na swoją korzyść i nie mogliby się bez nich obejść

Rajiv
źródło
Właściwie użyłem widoków indeksowanych (tylko raz) do podzielenia indeksu wyszukiwania pełnotekstowego. Indeksy FTS rzeczywiście nie mogą być podzielone na partycje, ale oddzielne indeksy można utworzyć w kilku widokach z tej samej tabeli. To była jednak ostateczność.
areyesram
4
Należy pamiętać o dodawaniu (NOEXPAND)podpowiedzi do zapytań korzystających z widoków indeksowanych. I wtedy zauważasz różnicę. Zaletą korzystania z widoków indeksowanych w porównaniu z „prawidłowym indeksowaniem tabel” jest ograniczenie wyboru rekordów, w przeciwnym razie miałbyś rację, byłoby tak samo.
ajeh
Tak, rzecz NOEXPAND nie może być zaniżona!
Simon_Weaver
18

Możesz potrzebować trochę więcej informacji na temat tego, czym właściwie jest zmaterializowany widok. W Oracle są to obiekty, które składają się z wielu elementów, gdy próbujesz zbudować go w innym miejscu.

MVIEW jest zasadniczo migawką danych z innego źródła. W przeciwieństwie do widoku dane nie zostaną znalezione podczas zapytania o widok, są one przechowywane lokalnie w postaci tabeli. MVIEW jest odświeżany za pomocą procedury działającej w tle, która uruchamia się w regularnych odstępach czasu lub gdy zmieniają się dane źródłowe. Oracle pozwala na pełne lub częściowe odświeżenia.

W SQL Server użyłbym następujących elementów do utworzenia podstawowego MVIEW w celu (pełnego) regularnego odświeżania.

Najpierw widok. Dla większości powinno to być łatwe, ponieważ widoki są dość powszechne w każdej bazie danych. Następnie tabela. Powinien być identyczny z widokiem w kolumnach i danych. Spowoduje to zapisanie migawki danych widoku. Następnie procedura obcina tabelę i ładuje ją ponownie na podstawie bieżących danych w widoku. Wreszcie zadanie, które uruchamia procedurę, aby rozpocząć pracę.

Wszystko inne to eksperymentowanie.

Jason A.
źródło
5
Twoje komentarze na temat SQL Server są niepoprawne - zmaterializowane widoki to bardzo różne rzeczy w Oracle i SQL Server. W SQL Server widok z unikalnym indeksem klastrowym (inaczej „widok zmaterializowany”) nie jest i nie może być aktualizowany przez użytkownika, ani nie jest przechowywany w oddzielnej tabeli utworzonej przez użytkownika - jest zawsze aktualizowany przez silnik podczas aktualizacji i nigdy nie jest zsynchronizowany. Przechowywanie migawki danych nie wymaga żadnego zadania.
ErikE
10
To, o co prosił PO, jest łatwo dostępne w zindeksowanym widoku. To najbliższa natywna rzecz SQL Server do zmaterializowanego widoku Oracle. Jeśli jednak chcesz / musisz dokładnie odtworzyć sposób działania Oracle MVIEW, Jason ma rację. Podejście Jasona pomaga również w tym samym scenariuszu, co Oracle MVIEWs - na przykład odświeżanie tabeli raportowania poza godzinami pracy, gdy bardziej zależy Ci na obciążeniu bazy danych niż na aktualności widoku (np. Raportowanie tylko wczorajszych liczb ...)
4

Gdy widok indeksowany nie wchodzi w grę, a szybkie aktualizacje nie są konieczne, możesz utworzyć tabelę pamięci podręcznej hackowania:

select * into cachetablename from myviewname
alter table cachetablename add primary key (columns)
-- OR alter table cachetablename add rid bigint identity primary key
create index...

następnie sp_rename view / table lub zmień wszelkie zapytania lub inne widoki, które odwołują się do niej, aby wskazywały na tabelę pamięci podręcznej.

planuj codziennie / co noc / co tydzień / jak odświeżać

begin transaction
truncate table cachetablename
insert into cachetablename select * from viewname
commit transaction

Uwaga: to zajmie miejsce, również w twoich dziennikach TX. Najlepiej sprawdza się w przypadku małych zbiorów danych, które wolno się obliczają. Może refaktoryzacja, aby najpierw wyeliminować „łatwe, ale duże” kolumny z widoku zewnętrznego.

stox
źródło
1

W przypadku MS T-SQL Server proponuję przyjrzeć się tworzeniu indeksu z instrukcją „include”. Niepowtarzalność nie jest wymagana, podobnie jak fizyczne sortowanie danych skojarzonych z indeksem klastrowym. Funkcja „Indeks ... Uwzględnij ()” tworzy oddzielny fizyczny magazyn danych automatycznie obsługiwany przez system. Koncepcyjnie jest bardzo podobny do zmaterializowanego widoku Oracle.

https://msdn.microsoft.com/en-us/library/ms190806.aspx

https://technet.microsoft.com/en-us/library/ms189607(v=sql.105).aspx

Scott Nightlinger
źródło