Índices Espaciais
Índices GiST aceleram operadores de caixa delimitadora e pré-filtragem de distância do PostGIS. Crie índices em colunas de geometria ou geografia, escreva consultas que usem && ou ST_DWithin, e mantenha estatísticas após cargas espaciais em massa.
Receita
CREATE TABLE parcels (
id bigserial PRIMARY KEY,
geom extensions.geometry(Polygon, 4326) NOT NULL
);
CREATE INDEX parcels_geom_gist ON parcels USING gist (geom);
-- Amigável ao índice: sobreposição de caixa delimitadora e depois filtro preciso
SELECT id
FROM parcels
WHERE geom && extensions.ST_Expand(
extensions.ST_SetSRID(extensions.ST_MakePoint(-73.99, 40.75), 4326),
0.01
)
AND extensions.ST_Contains(
geom,
extensions.ST_SetSRID(extensions.ST_MakePoint(-73.99, 40.75), 4326)
);Quando usar isso: Seq Scan em filtros espaciais, consultas de viewport de mapa, ou junção de grandes tabelas de polígonos.
Exemplo de Trabalho
CREATE TABLE drivers (
id uuid PRIMARY KEY,
loc extensions.geography(Point, 4326) NOT NULL,
updated_at timestamptz DEFAULT now()
);
CREATE INDEX drivers_loc_gist ON drivers USING gist (loc);
-- ST_DWithin usa índice para geografia
EXPLAIN (ANALYZE, BUFFERS)
SELECT id, updated_at
FROM drivers
WHERE extensions.ST_DWithin(
loc,
extensions.ST_SetSRID(extensions.ST_MakePoint(-73.99, 40.75), 4326)::extensions.geography,
1500 -- metros
)
ORDER BY updated_at DESC
LIMIT 50;
ANALYZE drivers;O que isso demonstra:
- GiST em
geographypara consultas de raio em metros ST_DWithiné o filtro de proximidade indexado idiomáticoEXPLAINdeve mostrarIndex Scan using drivers_loc_gistANALYZEapós atualizações de localização em massa
Mergulho Profundo
GiST vs SP-GiST
| Índice | Uso no PostGIS | Notas |
|---|---|---|
| GiST | Padrão para geometria/geografia | Maduro, propósito geral |
| SP-GiST | Algumas cargas de trabalho com muitos pontos | Teste antes da adoção ampla |
| BRIN | Tabelas enormes, geom ordenadas por inserção | Raro para dados espaciais irregulares |
Escolha padrão: GiST, a menos que benchmarks mostrem o contrário.
Operadores Que Usam GiST
-- sobreposição de caixa delimitadora de geometria (indexável)
geom1 && geom2
-- ST_DWithin com índice (usa && internamente para pré-filtragem)
ST_DWithin(geog1, geog2, distance_meters)Funções que usam apenas geometria exata sem pré-filtragem de caixa delimitadora podem não usar o índice eficientemente (ST_Contains sozinho em uma tabela enorme sem guarda &&).
Índices de Múltiplas Colunas e Parciais
-- Apenas motoristas ativos
CREATE INDEX drivers_active_loc_gist ON drivers USING gist (loc)
WHERE updated_at > now() - interval '1 hour';
-- Btree composto + gist: filtra tenant e depois espacial
CREATE INDEX parcels_tenant_gist ON parcels (tenant_id);
CREATE INDEX parcels_geom_gist ON parcels USING gist (geom);Aplique igualdade de tenant_id antes da operação espacial para SaaS multitenant.
Construção e Manutenção de Índice
CREATE INDEX CONCURRENTLY parcels_geom_gist ON parcels USING gist (geom);
-- Após importação de shapefile em massa
REINDEX INDEX CONCURRENTLY parcels_geom_gist;
ANALYZE parcels;
SELECT pg_size_pretty(pg_relation_size('parcels_geom_gist'));Polígonos complexos produzem árvores GiST grandes. Simplifique geometrias para índices de visão geral, se necessário (veja o artigo de desempenho).
Checklist de Plano de Consulta
EXPLAIN (ANALYZE, BUFFERS)
SELECT ...
-- Esperar: Index Scan using ..._gist
-- Sinal de alerta: Seq Scan + Filter em milhões de linhasArmadilhas
- Nenhum índice em cast de geografia apenas no WHERE - Expressão não indexada. Correção: Persista a coluna de geografia ou indexe a expressão funcional explicitamente.
- ST_Distance sem DWithin - Ordena todas as linhas. Correção: Limite
ST_DWithine depoisORDER BY ST_Distanceem um conjunto pequeno. - SRID incorreto na coluna do índice - Índice usado, mas respostas erradas. Correção: Restrições de SRID no typmod da coluna.
- Caixa delimitadora minúscula -
&&excessivamente seletivo perde as bordas. Correção:ST_Expandou tolerância apropriada. - Bloqueio CREATE INDEX - Bloqueia escritas em produção. Correção:
CONCURRENTLY. - Estatísticas desatualizadas após importação GIS em massa -
Seq scanescolhido. Correção:ANALYZEe considere aumentardefault_statistics_targetem colunas de geometria, se suportado pela carga de trabalho.
Alternativas
| Alternativa | Usar Quando | Não Usar Quando |
|---|---|---|
| BRIN em pontos clusterizados | Logs de GPS ordenados por tempo | Distribuição espacial aleatória |
| Sem índice (tabela minúscula) | < 5k features | Camadas de mapa de produção |
| Blocos de grade pré-computados | Vetores somente leitura | Vetores editados frequentemente |
| Índice espacial externo | ES geo_shape | Junções espaciais relacionais |
FAQs
Tamanho do índice GiST?
Depende da contagem de vértices; polígonos complexos são maiores que pontos. Monitore pg_relation_size.Índice de geography vs geometry?
Ambos usam GiST; consulte com tipo correspondente e ST_DWithin.Índice clusterizado?
CLUSTER em GiST raramente usado; particionamento é mais comum.Índice de geometria 3D?
GiST suporta; certifique-se de que as funções correspondem à dimensionalidade.Múltiplas colunas de geometria?
GiST separado por coluna usada em consultas.Operador &&?
Sobreposição de caixa delimitadora; padrão central de aceleração de índice.ORDER BY KNN?
Operador <-> para KNN de geometria em coluna indexada em consultas suportadas.Replicação?
Índices replicam com DDL de tabela em replicação física.Vacuum?
GiST se beneficia de vacuum rotineiro após atualizações pesadas.Limites da nuvem?
Algumas instâncias limitam construções de índice concorrentes; agende manutenção.Relacionados
- Geometria vs Geografia - escolha de tipo
- Desempenho do PostGIS - simplificar e pré-filtrar
- GIN e GiST - visão geral do GiST
- Noções Básicas de Design de Índice - indexação geral
- Melhores Práticas do PostGIS - validar entradas
Versões da Stack: Esta página foi escrita para PostgreSQL 18.4 (estável 18, manutenção 17), pgvector 0.8+, PostGIS 3.5+, pgbouncer 1.x, e Patroni 3.x.