Notatka
Dostęp do tej strony wymaga autoryzacji. Może spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
DiskANN to skalowalny przybliżony algorytm wyszukiwania najbliższych sąsiadów umożliwiający wydajne wyszukiwanie wektorów w dowolnej skali. Oferuje wysoką trafność, dużą liczbę zapytań na sekundę i niskie opóźnienie zapytań, nawet dla zbiorów danych liczących miliardy punktów. Te cechy sprawiają, że jest to zaawansowane narzędzie do obsługi dużych ilości danych.
Aby dowiedzieć się więcej na temat DiskANN, zobacz DiskANN: Wyszukiwanie wektorowe w skali sieci Web i rekomendacje.
Rozszerzenie pg_diskann dodaje obsługę wykorzystywania DiskANN do efektywnego indeksowania i wyszukiwania wektorów.
Włącz pg_diskann
Aby użyć pg_diskann rozszerzenia na serwerze elastycznym Azure Database for PostgreSQL, należy zezwolić na rozszerzenie na poziomie serwera. Następnie należy utworzyć rozszerzenie dla każdej bazy danych, w której chcesz użyć funkcji udostępnianych przez rozszerzenie.
Ponieważ pg_diskann ma zależność od rozszerzenia vector, albo zezwól, albo utwórz rozszerzenie vector w tej samej bazie danych, a następnie uruchom następujące polecenie:
CREATE EXTENSION IF NOT EXISTS pg_diskann;
Możesz też pominąć jawne zezwalanie i tworzenie vector rozszerzenia, a zamiast tego uruchomić poprzednie polecenie dołączając klauzulę CASCADE . Klauzula PostgreSQL automatycznie uruchamia polecenie CREATE EXTENSION dla rozszerzenia, od którego zależy system. W tym celu uruchom następujące polecenie:
CREATE EXTENSION IF NOT EXISTS pg_diskann CASCADE;
Aby usunąć rozszerzenie z bazy danych, do której aktualnie nawiązane połączenie, uruchom następujące polecenie:
DROP EXTENSION IF EXISTS pg_diskann;
Korzystanie z metody dostępu do indeksu diskann
Po zainstalowaniu rozszerzenia można utworzyć diskann indeks w kolumnie tabeli zawierającej dane wektorowe. Aby na przykład utworzyć indeks w embedding kolumnie demo tabeli, użyj następującego polecenia:
CREATE TABLE demo (
id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
embedding public.vector(3)
-- other columns
);
-- insert dummy data
INSERT INTO demo (embedding) VALUES
('[1.0, 2.0, 3.0]'),
('[4.0, 5.0, 6.0]'),
('[7.0, 8.0, 9.0]');
-- create a diskann index by using Cosine distance operator
CREATE INDEX demo_embedding_diskann_idx ON demo USING diskann (embedding vector_cosine_ops)
Po utworzeniu indeksu można uruchamiać zapytania, aby znaleźć najbliższych sąsiadów.
Poniższe zapytanie wyszukuje pięciu najbliższych sąsiadów wektora [2.0, 3.0, 4.0]:
SELECT id, embedding
FROM demo
ORDER BY embedding <=> '[2.0, 3.0, 4.0]'
LIMIT 5;
Usługa Postgres automatycznie decyduje, kiedy używać indeksu DiskANN. Jeśli zdecyduje się nie używać indeksu w scenariuszu, w którym ma używać indeksu, wykonaj następujące polecenie:
-- Explicit Transcation block to force use for DiskANN index.
BEGIN;
SET LOCAL enable_seqscan TO OFF;
-- Similarity search queries
COMMIT;
Ważne
Ustawienie enable_seqscan wartości wyłączonej zniechęca planistę do korzystania z planu skanowania sekwencyjnego przez planistę zapytań, jeśli istnieją inne dostępne metody. Ponieważ jest ona wyłączona za pomocą SET LOCAL polecenia , ustawienie ma zastosowanie tylko dla bieżącej transakcji. Po wykonaniu operacji COMMIT lub ROLLBACK, ustawienie poziomu sesji ponownie wchodzi w życie. Jeśli zapytanie obejmuje inne tabele, ustawienie również zniechęca do korzystania ze skanowania sekwencyjnego we wszystkich z nich.
Wydajne skalowanie przy użyciu kwantyzacji (wersja zapoznawcza)
Funkcja DiskANN używa kwantyzacji produktu (PQ), aby znacznie zmniejszyć zużycie pamięci wektorów. W przeciwieństwie do innych technik kwantyzacji algorytm PQ może bardziej efektywnie kompresować wektory, co znacznie poprawia wydajność. Korzystając z PQ, diskANN może zachować więcej danych w pamięci, zmniejszyć potrzebę uzyskania dostępu do wolniejszego magazynu i użyć mniejszej mocy obliczeniowej podczas porównywania skompresowanych wektorów. Skutkuje to lepszą wydajnością i znacznymi oszczędnościami kosztów podczas pracy z większymi ilościami danych (> 1 milion wierszy).
Ważne
Obsługa kwantyzacji produktu na serwerze DiskANN jest dostępna od wersji pg_diskann w wersji 0.6 lub nowszej.
Aby zmniejszyć rozmiar indeksu i dopasować więcej danych do pamięci, użyj PQ:
CREATE INDEX demo_embedding_diskann_idx ON demo USING diskann(embedding vector_cosine_ops)
WITH(
product_quantized=true
);
Zwiększ dokładność podczas korzystania z PQ z wektorowym ponownym rankingowaniem
Ponowne rangowanie z użyciem pełnych wektorów to technika stosowana w systemach wyszukiwania przybliżonych najbliższych sąsiadów (ANN), takich jak DiskANN z kwantyzacją produktu (PQ), w celu zwiększenia dokładności wyników poprzez ponowne uporządkowanie pierwszych N pobranych kandydatów na podstawie oryginalnych, nieskompresowanych wektorów (o pełnej precyzji). Ta technika ponownego rankingowania opiera się wyłącznie na metrykach dokładnego podobieństwa wektorów (na przykład podobieństwie cosinusowym lub odległości euklidesowej). Ta technika nie jest tym samym co ponowne rankingowanie przy użyciu modelu rankingowego.
Aby zrównoważyć szybkość i precyzję wyszukiwania podobnych wektorów, zastosuj dwuetapową strategię ponownego uszeregowania wyników podczas wykonywania zapytań przy użyciu DiskANN i kwantyzacji iloczynowej w celu zwiększenia dokładności.
Wstępne wyszukiwanie przybliżone: Zapytanie wewnętrzne korzysta z algorytmu DiskANN, aby pobrać 50 najlepszych przybliżonych najbliższych sąsiadów na podstawie odległości cosinusowej między zapisanymi embeddingami a wektorem zapytania. Ten krok jest szybki i wydajny, wykorzystując możliwości indeksowania diskANN.
Precyzyjne ponowne rangowanie: Zapytanie zewnętrzne zmienia kolejność tych 50 wyników na podstawie faktycznie obliczonej odległości i zwraca 10 najtrafniejszych wyników:
Oto przykład ponownego rankingowania z zastosowaniem tego dwuetapowego podejścia:
SELECT id
FROM (
SELECT id, embedding <=> %s::vector AS distance
FROM demo
ORDER BY embedding <=> %s::vector asc
LIMIT 50
) AS t
ORDER BY t.distance
LIMIT 10;
Uwaga / Notatka
Zastąp %s wektorem zapytania. Za pomocą azure_ai można utworzyć wektor zapytania bezpośrednio w usłudze Postgres.
Takie podejście równoważy szybkość (za pośrednictwem przybliżonego wyszukiwania) i dokładności (za pośrednictwem pełnego korbowania wektorowego), zapewniając wysokiej jakości wyniki bez skanowania całego zestawu danych.
Obsługa osadzania o wysokim wymiarze
Zaawansowane aplikacje generatywnej sztucznej inteligencji często opierają się na modelach embeddingowych o wysokiej wymiarowości, takich jak text-embedding-3-large, aby osiągnąć wyższą dokładność. Jednak tradycyjne metody indeksowania, takie jak HNSW w wektorach pgvector , są ograniczone do wektorów z maksymalnie 2000 wymiarami, co ogranicza użycie tych zaawansowanych modeli.
Począwszy od pg_diskann w wersji 0.6 lub nowszej, funkcja DiskANN obsługuje wektory indeksowania z maksymalnie 16 000 wymiarami, co znacznie zwiększa zakres obciążeń sztucznej inteligencji o wysokiej dokładności.
Ważne
Włącz funkcję Product Quantization, aby wykorzystać obsługę danych wysokowymiarowych.
Zalecane ustawienia:
-
product_quantized: Ustaw na wartość true -
pq_param_num_chunks: ustaw na jedną trzecią wymiaru osadzania, aby uzyskać optymalną wydajność. -
pq_param_training_samples: Automatycznie określana na podstawie rozmiaru tabeli, chyba że jawnie ustawiono.
To ulepszenie umożliwia skalowalne i wydajne wyszukiwanie w dużych zbiorach danych wektorowych przy zachowaniu wysokiej czułości i precyzji.
Przyspieszanie kompilacji indeksu
Aby poprawić czas kompilacji indeksu, wypróbuj następujące zalecenia.
Korzystanie z większej ilości pamięci
Aby przyspieszyć tworzenie indeksu, zwiększ ilość pamięci przydzielonej na serwerze PostgreSQL na potrzeby kompilacji indeksu. Określ użycie pamięci za pomocą parametru maintenance_work_mem .
-- Set the parameters
SET maintenance_work_mem = '8GB'; -- Depending on your resources
Polecenie CREATE INDEX używa określonej pamięci roboczej, w zależności od dostępnych zasobów, do skompilowania indeksu.
CREATE INDEX demo_embedding_diskann_idx ON demo USING diskann (embedding vector_cosine_ops)
Wskazówka
Zwiększ zasoby pamięci podczas tworzenia indeksu, aby przyspieszyć indeksowanie, a następnie zmniejsz je po zakończeniu indeksowania.
Korzystanie z przetwarzania równoległego
Aby przyspieszyć tworzenie indeksu, użyj równoległych procesów roboczych. Określ liczbę procesów roboczych za pomocą parametru pamięci masowej parallel_workers instrukcji CREATE TABLE podczas tworzenia tabeli. Tę liczbę można później dostosować za pomocą klauzuli SET instrukcji ALTER TABLE.
CREATE TABLE demo (
id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
embedding public.vector(3)
) WITH (parallel_workers = 4);
ALTER TABLE demo SET (parallel_workers = 8);
Polecenie CREATE INDEX używa określonej liczby równoległych procesów roboczych, w zależności od dostępnych zasobów, do utworzenia indeksu.
CREATE INDEX demo_embedding_diskann_idx ON demo USING diskann (embedding vector_cosine_ops)
Ważne
Proces główny nie może uczestniczyć w równoległym tworzeniu indeksów.
Jeśli chcesz utworzyć indeks za pomocą równoległych procesów roboczych, ustaw odpowiednio parametry max_parallel_workers, max_worker_processes i max_parallel_maintenance_workers. Aby uzyskać więcej informacji na temat tych parametrów, zobacz parametry kontrolujące użycie zasobów i zachowanie asynchroniczne.
Ustaw te parametry na różnych poziomach szczegółowości. Aby na przykład ustawić je na poziomie sesji, uruchom następujące instrukcje:
-- Set the parameters
SET max_parallel_workers = 8;
SET max_worker_processes = 8; -- Note: Requires server restart
SET max_parallel_maintenance_workers = 4;
Aby dowiedzieć się więcej o innych opcjach konfigurowania tych parametrów na serwerze elastycznym Azure Database for PostgreSQL, zobacz Konfigurowanie parametrów.
Uwaga / Notatka
Parametr max_worker_processes wymaga ponownego uruchomienia serwera, aby zaczęły obowiązywać.
Jeśli konfiguracja tych parametrów i dostępnych zasobów na serwerze nie zezwalają na uruchamianie równoległych procesów roboczych, program PostgreSQL automatycznie wraca do tworzenia indeksu w trybie nieparallelowym.
Parametry konfiguracji
Podczas tworzenia indeksu diskann określ różne parametry, aby kontrolować jego zachowanie.
Parametry indeksu
-
max_neighbors: Maksymalna liczba krawędzi na węzeł na wykresie. Wartość domyślna to 32. Wyższa wartość może poprawić przypominanie do pewnego punktu. -
l_value_ib: rozmiar listy wyszukiwania podczas kompilacji indeksu. Wartość domyślna to 100. Wyższa wartość sprawia, że kompilacja jest wolniejsza, ale indeks jest o wyższej jakości. -
product_quantized: umożliwia kwantyzację produktu w celu bardziej wydajnego wyszukiwania. Wartość domyślna to fałsz. -
pq_param_num_chunks: Liczba fragmentów kwantyzacji produktu. Wartość domyślna to 0, co oznacza, że system automatycznie określa wartość na podstawie osadzonych wymiarów. Użyj jednej trzeciej oryginalnych wymiarów osadzania. -
pq_param_training_samples: Liczba wektorów używanych do trenowania tabeli pivotów PQ. Wartość domyślna to 0, co oznacza, że system automatycznie określa wartość na podstawie rozmiaru tabeli.
CREATE INDEX demo_embedding_diskann_custom_idx ON demo USING diskann (embedding vector_cosine_ops)
WITH (
max_neighbors = 48,
l_value_ib = 100,
product_quantized=true,
pq_param_num_chunks = 0,
pq_param_training_samples = 0
);
Parametry rozszerzenia
diskann.iterative_search: steruje zachowaniem wyszukiwania.Konfiguracje dla programu
diskann.iterative_search:relaxed_order(ustawienie domyślne): Umożliwia iteracyjne przeszukiwanie wykresu w partiachdiskann.l_value_is, aż do osiągnięcia żądanej liczby krotek, która może być ograniczona przez klauzulęLIMIT. Ta opcja może spowodować, że wyniki będą wyświetlane w niewłaściwej kolejności.strict_order: Podobny dorelaxed_order, ale gwarantuje, że wyniki są zwracane w ścisłej kolejności posortowanej według odległości.off: używa funkcji wyszukiwania nieteratywnego. Próbuje pobraćdiskann.l_value_iskrotki w jednym kroku. Wyszukiwanie nieteratywne może zwracać co najwyżejdiskann.l_value_iswektorów dla zapytania, niezależnie od klauzuli zapytania czy liczby krotek pasujących do zapytania.
Aby zmienić zachowanie
strict_orderwyszukiwania dla wszystkich zapytań wykonywanych w bieżącej sesji, uruchom następującą instrukcję:SET diskann.iterative_search TO 'strict_order';Aby ją zmienić tak, aby dotyczyła tylko wszystkich zapytań wykonywanych w bieżącej transakcji, uruchom następującą instrukcję:
BEGIN; SET LOCAL diskann.iterative_search TO 'strict_order'; -- All your queries COMMIT;diskann.l_value_is: wartość L na potrzeby skanowania indeksów (domyślnie to 100). Zwiększenie wartości poprawia przywołanie, ale może spowolnić wykonywanie zapytań.Aby zmienić wartość L skanowania indeksu na 20 dla wszystkich zapytań wykonanych w bieżącej sesji, uruchom następującą instrukcję:
SET diskann.l_value_is TO 20;Aby ją zmienić tak, aby dotyczyła tylko wszystkich zapytań wykonywanych w bieżącej transakcji, uruchom następującą instrukcję:
BEGIN; SET LOCAL diskann.l_value_is TO 20; -- All your queries COMMIT;
Zalecana konfiguracja parametrów
| Rozmiar zestawu danych (wiersze) | Typ parametru | Name | Zalecana wartość |
|---|---|---|---|
| <1 mln | Budowanie indeksu | l_value_ib |
100 |
| <1 mln | Budowanie indeksu | max_neighbors |
32 |
| <1 mln | Czas zapytania | diskann.l_value_is |
100 |
| 1M-50M | Budowanie indeksu | l_value_ib |
100 |
| 1M-50M | Budowanie indeksu | max_neighbors |
64 |
| 1M-50M | Budowanie indeksu | product_quantized |
true |
| 1M-50M | Czas zapytania | diskann.l_value_is |
100 |
| >50 mln | Budowanie indeksu | l_value_ib |
100 |
| >50 mln | Budowanie indeksu | max_neighbors |
96 |
| >50 mln | Budowanie indeksu | product_quantized |
true |
| >50 mln | Czas zapytania | diskann.l_value_is |
100 |
Uwaga / Notatka
Te parametry mogą się różnić w zależności od określonego zestawu danych i przypadku użycia. Może być konieczne eksperymentowanie z różnymi wartościami parametrów, aby znaleźć optymalne ustawienia dla danego scenariusza.
Postęp operacji CREATE INDEX i REINDEX
Począwszy od bazy danych PostgreSQL 12, możesz użyć pg_stat_progress_create_index polecenia , aby sprawdzić postęp operacji CREATE INDEX lub REINDEX.
SELECT phase, round(100.0 * blocks_done / nullif(blocks_total, 0), 1) AS "%" FROM pg_stat_progress_create_index;
Aby dowiedzieć się więcej na temat możliwych faz, za pomocą których przechodzi operacja CREATE INDEX lub REINDEX, zobacz CREATE INDEX phases (FAZY TWORZENIA INDEKSU).
Wybieranie funkcji dostępu do indeksu
Typ wektora obsługuje trzy typy wyszukiwań w przechowywanych wektorach. Wybierz prawidłową funkcję dostępu dla indeksu, aby baza danych mogła rozważyć indeks podczas wykonywania zapytań.
pg_diskann obsługuje następujące operatory odległości:
-
vector_l2_ops:<->Odległość euklidesowa -
vector_cosine_ops:<=>Odległość kosinusowa -
vector_ip_ops:<#>Produkt wewnętrzny
Rozwiązywanie problemów
Błąd: : assertion left == right failed left: 40 right: 0
Wersja GA DiskANN, v0.6.x wprowadza zmiany niekompatybilne w formacie metadanych indeksu. Indeksy utworzone za pomocą wersji 0.5.x nie są zgodne z operacjami wstawiania w wersji 0.6.x. Jeśli spróbujesz wstawić do tabeli z nieaktualnym indeksem, wystąpi błąd, nawet jeśli indeks jest prawidłowy.
Jeśli wystąpi ten błąd, rozwiąż go, wykonując następujące czynności:
Opcja 1: Wykonanie instrukcji
REINDEXlubREDINDEX CONCURRENTLYw indeksie.Opcja 2: Ponowne kompilowanie indeksu.
DROP INDEX your_index_name; CREATE INDEX your_index_name ON your_table USING diskann(your_vector_column vector_cosine_ops);
Błąd: : diskann index needs to be upgraded to version 2...
- Gdy wystąpi ten błąd, rozwiąż go w następujący sposób:
Opcja 1: Wykonanie instrukcji
REINDEXlubREDINDEX CONCURRENTLYw indeksie.Opcja 2: Ze względu
REINDEXna to, że rozszerzenie może zająć dużo czasu, udostępnia również funkcję zdefiniowaną przez użytkownika o nazwieupgrade_diskann_index(), która uaktualnia indeks szybciej, gdy jest to możliwe.Aby uaktualnić indeks, uruchom następującą instrukcję:
SELECT upgrade_diskann_index('demo_embedding_diskann_custom_idx');Aby uaktualnić wszystkie indeksy diskann w bazie danych do bieżącej wersji, uruchom następującą instrukcję:
SELECT upgrade_diskann_index(pg_class.oid) FROM pg_class JOIN pg_am ON (pg_class.relam = pg_am.oid) WHERE pg_am.amname = 'diskann';