PostgreSQL
 sql >> Baza danych >  >> RDS >> PostgreSQL

Zmaterializowana ścieżka Postgres - Jakie są korzyści z używania ltree?

TL;DR Etykiety wielokrotnego użytku, złożone wzorce wyszukiwania i wyszukiwania przodków w wielu węzłach potomnych (lub pojedynczym węźle, którego ścieżka nie została jeszcze pobrana) nie mogą być wykonane przy użyciu zmaterializowanego indeksu ścieżki.

Dla zainteresowanych krwawymi szczegółami...

Po pierwsze, twoje pytanie jest istotne tylko wtedy, gdy nie używasz ponownie żadnych etykiet w opisie węzła. Jeśli tak, l-drzewo jest naprawdę jedyną opcją z tych dwóch. Ale implementacje zmaterializowanych ścieżek zazwyczaj tego nie potrzebują, więc odłóżmy to na bok.

Jedną z oczywistych różnic będzie elastyczność w typach wyszukiwań, które zapewnia l-tree. Rozważ te przykłady (z ltree dokumenty, do których prowadzą linki w Twoim pytaniu):

foo         Match the exact label path foo
*.foo.*     Match any label path containing the label foo
*.foo       Match any label path whose last label is foo

Pierwsze zapytanie jest oczywiście osiągalne ze zmaterializowaną ścieżką. Ostatni jest również osiągalny, gdzie można dostosować zapytanie jako wyszukiwanie rodzeństwa. Jednak środkowy przypadek nie jest bezpośrednio osiągalny za pomocą pojedynczego wyszukiwania indeksu. Musisz albo podzielić to na dwa zapytania (wszyscy potomkowie + wszyscy przodkowie), albo uciec się do skanowania tabeli.

A potem są naprawdę złożone zapytania, takie jak to (również z dokumentacji):

Top.*{0,2}.sport*@.!football|tennis.Russ*|Spain

Zmaterializowany indeks ścieżki byłby tutaj bezużyteczny, a do obsługi tego byłoby wymagane pełne skanowanie tabeli. l-tree jest jedyną opcją, jeśli chcesz wykonać to jako zapytanie SARGable.

Ale w przypadku standardowych operacji hierarchicznych można znaleźć dowolne z:

  • rodzic
  • dzieci
  • potomkowie
  • węzły główne
  • węzły liści

zmaterializowana ścieżka będzie działać tak samo dobrze jak l-drzewo. W przeciwieństwie do artykułu, do którego link znajduje się powyżej , wyszukiwanie wszystkich potomków wspólnego przodka jest bardzo wykonalne przy użyciu b-drzewa. Format zapytania WHERE path LIKE 'A.%' jest SARGable pod warunkiem, że twój indeks jest przygotowany poprawnie (musiałem wyraźnie oznaczyć mój indeks ścieżki za pomocą varchar_pattern_ops aby to zadziałało).

To, czego brakuje na tej liście, to znalezienie wszystkich przodków dla potomka. Format zapytania WHERE 'A.B.C.D' LIKE path || '.%' niestety nie będzie korzystał z indeksu. Jednym z obejść, które implementują niektóre biblioteki, jest przeanalizowanie węzłów przodków ze ścieżki i bezpośrednie zapytanie:WHERE id IN ('A', 'B', 'C') . Jednak będzie to działać tylko wtedy, gdy celujesz w przodków określonego węzła, którego ścieżkę już pobrałeś. W tym przypadku wygra l-drzewo.




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Wyliczone typy z ActiveRecord i Postgresql

  2. Surowe zapytanie PostgreSQL zawiesza się po wykonaniu z TypeOrm

  3. lokalna baza danych postgres stale podaje błąd zduplikowanej wartości klucza narusza unikalność

  4. Aktualizowanie kolumny typu integer z elementu jsonb kończy się niepowodzeniem:kolumna jest typu integer, ale wyrażenie jest typu jsonb

  5. Wydajność obliczeń i sortowania Delta E (CIE Lab) w SQL