Mam tabelę z dużą ilością wstawek, ustawiając jedno z pól ( uploaded_at
) na NULL
. Następnie okresowe zadanie wybiera wszystkie krotki WHERE uploaded_at IS NULL
, przetwarza je i aktualizuje, ustawiając uploaded_at
na bieżącą datę.
Jak powinienem indeksować tabelę?
Rozumiem, że powinienem użyć częściowego indeksu, takiego jak:
CREATE INDEX foo ON table (uploaded_at) WHERE uploaded_at IS NULL
Lub coś w tym rodzaju. Jestem trochę zdezorientowany, jeśli poprawne jest indeksowanie na polu, które jest zawsze NULL
. Lub jeśli poprawne jest użycie indeksu b-drzewa. Hash wygląda na lepszy pomysł, ale jest przestarzały i nie jest replikowany przez przesyłanie strumieniowe replikacji w trybie gotowości. Wszelkie porady będą mile widziane.
Eksperymentowałem trochę z następującymi indeksami:
"foo_part" btree (uploaded_at) WHERE uploaded_at IS NULL
"foo_part_id" btree (id) WHERE uploaded_at IS NULL
a narzędzie do planowania zapytań zawsze wybiera foo_part
indeks. explain analyse
daje również nieco lepszy wynik dla foo_part
indeksu:
Index Scan using foo_part on t1 (cost=0.28..297.25 rows=4433 width=16) (actual time=0.025..3.649 rows=4351 loops=1)
Index Cond: (uploaded_at IS NULL)
Total runtime: 4.060 ms
vs
Bitmap Heap Scan on t1 (cost=79.15..6722.83 rows=4433 width=16) (actual time=1.032..4.717 rows=4351 loops=1)
Recheck Cond: (uploaded_at IS NULL)
-> Bitmap Index Scan on foo_part_id (cost=0.00..78.04 rows=4433 width=0) (actual time=0.649..0.649 rows=4351 loops=1)
Total runtime: 5.131 ms
źródło
id
na przykład pole szeregowe ?serial
jest tak dobry, jak każdy inny. Chodzi o to, czy faktycznie istnieją zapytania, aby z nich skorzystać.