Quando você NÃO deve usar um índice espacial?

29

Estou perguntando isso, porque eu estava trabalhando principalmente com a Oracle, mas, no ano passado, tenho dobrado com o PostGIS e o SQLServer 2008. A maioria das funções espaciais no Oracle não funciona sem um índice espacial retornando o erro ORA-13226:

13226, 00000, "interface não suportada sem um índice espacial" // * Causa: a tabela de geometria não possui um índice espacial. // * Ação: verifique se a tabela de geometria referenciada no operador espacial possui um índice espacial.

Para mim, isso faz sentido. Você executa uma consulta espacial = deve ter um índice espacial. Mas, tanto quanto eu entendo, nem o PostGIS, nem o SQL Serve exigem isso. O PostGIS até parece ter funções (_ * por exemplo, _STContains) que EXPLICITAMENTE não usarão o índice espacial.

Portanto, a questão é: existem casos em que você NÃO deve usar um índice espacial? Não necessariamente se é uma abordagem de “pegar ou largar”, ou seja, não fará diferença, mas onde NÃO usar o índice espacial afetará o desempenho? Para mim, a última frase é uma contradição em termos, mas por que o PostGIS forneceria essas funções?

mapoholic
fonte
3
Se você deseja ver onde um índice torna as coisas mais lentas no PostGIS SET enable_seqscan = off. Isso forçará o PostgreSQL a usar índices sempre. Compare as velocidades com ele.
27711 Sean
Obrigado por iniciar esta discussão. Venho pesquisando informações na rede, tentando descobrir por que minha organização (governo) não faz uso de índices espaciais (ou mesmo de atributos) em suas classes e tabelas de recursos do oracle / sde. Agora, tenho alguns argumentos para apresentar a eles, para que eu não precise arrancar meus cabelos, esperando que uma consulta se resolva.
Mike

Respostas:

12

mapoholic,

De um modo geral, não há uma razão para fazer uma consulta espacial sem um índice espacial, a menos que você esteja lidando com tabelas realmente pequenas. Mesmo assim, você usaria o ST_ que não usa um índice, mas possui os operadores de caixa de curto-circuito indexável &&. as funções que começam com _ST não devem ser usadas pelos usuários finais. A razão de existirem é porque precisam. Os índices espaciais do PostGIS usam o SQL inlining para forçar o uso do índice - o _ST geralmente é feito pelo GEOS e o && é o índice que pode ser reordenado. Portanto, o _ST é realmente um artefato de implementação.

então, resumindo, não é uma função para que a operação do índice possa ser reordenada para acontecer de uma só vez antes da verificação espacial mais intensa.

LR1234567
fonte
Cheers LR1234567. Eu acho que é isso que eu estava procurando.
mapoholic
25

Se o seu conjunto de dados for adicionado e atualizado com freqüência, as instruções INSERT, DELETE e UPDATE que causam a reconstrução do índice podem tornar o banco de dados lento.

Para inserções em massa, como carregar todo o conjunto de dados OSM em um banco de dados, pode ser mais rápido descartar os índices e criá-los novamente posteriormente.

Se for mais eficiente ignorar um índice (por exemplo, a tabela é pequena o suficiente para ser carregada na memória), o processador de consultas ao banco de dados deve fazer isso automaticamente.

Eu esperaria que o principal motivo para permitir que consultas sejam executadas sem um índice espacial seja medir os benefícios de desempenho que você obtém usando um índice, sem ter que eliminá-lo.

Finalmente, se você deseja mostrar um enorme aumento de desempenho nas consultas e nas exibições de mapas, pode adiar a criação de índices para um momento oportuno no desenvolvimento do sistema ...

geographika
fonte
3
(+1) Detecto um pouco de cinismo nessa última observação? :-)
whuber
Nem um pouco ;-) Mas descartar / recriar índices cuidadosamente ajustados é uma resposta útil para "Por que X gastou muito tempo em alterações no banco de dados"?
geografika
Obrigado geographica- e eu concordo com a observação do whuber! ;-) Entendo que você eliminaria / desabilitaria os índices espaciais ao carregar em massa - ou todos os índices, mas não consegue pensar em uma razão para fazer uma consulta espacial SEM usar um índice espacial? Se uma tabela é pequena o suficiente, o uso do índice pode não fazer a diferença - justa o suficiente -, mas optando por não usar o índice ?. Não sei, acho que eu apenas estou perplexo mais com a existência das funções de PostGIS não-espacial-índice ...
mapoholic
2
Se uma tabela é pequena o suficiente e se encaixa na memória, o uso de um índice requer acesso aleatório ao disco, que é mais caro do que uma varredura seqüencial. wiki.postgresql.org/wiki/…
Sean
2
@mapoholic - os _ST_Contains poderia ser sobraram de quando você tinha que fazer manualmente um pré-filtro de seus dados, a julgar old.nabble.com/...
geographika
10

Eu acho que isso está implícito, mas eu NÃO usaria um índice espacial para uma consulta quando tivesse um índice não espacial que pudesse usar. Por exemplo, tenho 2.113.450 pontos que abrangem os Estados Unidos carregados em uma tabela. Se eu quisesse extrair todos os pontos que estavam dentro do estado do Alasca, poderia fazer uma consulta espacial que usasse o índice GIST nas geometrias de pontos para comparar com a geometria do estado do Alasca, OU, poderia apenas usar o campo "state_alpha" nos dados do ponto (que também é indexado) para retornar todos os pontos que possuem "state_alpha" = 'AK'.

"Onde está a parte espacial disso", você pergunta? Bem, se eu precisar fazer algumas análises espaciais adicionais nos pontos Alaska_ depois de colecioná-los, é mais rápido reunir essas geometrias de pontos usando uma consulta não espacial primeiro. Isso também significa que, para conjuntos de dados realmente grandes, você se beneficia da adição de um campo de pesquisa (ou tabela). Novamente, eu sei que isso provavelmente é óbvio para todos, já o mencionei porque o encontrei no passado com conjuntos de dados globais indexados espacialmente e onde uma consulta comum era "todos os recursos de um país". Obtivemos muito desempenho adicionando um campo indexado country_fips.

Abaixo estão alguns resultados de EXPLAIN ANALYZE que comprovam o argumento. (NOTA: Tentei tornar a consulta espacial o mais eficiente possível usando uma consulta BBOX. O uso dos contornos de estado só a tornaria mais lenta.)

# explain analyze select count(*) from gnis_names where state_alpha = 'AK';
Aggregate  (cost=57359.45..57359.46 rows=1 width=0) (actual time=76.606.. 76.607 rows=1 loops=1)
<snip>
Total runtime: 76.676 ms

# explain analyze select count(*) from gnis_names where the_geom && GeomFromText('POLYGON((-179.14734 51.219862,-179.14734 71.3525606439998,179.77847 71.3525606439998,179.77847 51.219862,-179.14734 51.219862))',4326);
Aggregate  (cost=27699.86..27699.87 rows=1 width=0) (actual time=86.523..86.524 rows=1 loops=1)
<snip>
Total runtime: 86.584 ms 
lagerratrobe
fonte
Muito obrigado por isso. Pode parecer óbvio quando você diz isso, mas meu primeiro pensamento seria executar uma consulta espacial e não apenas um atributo. +1 para isso!
mapoholic
0

Só notei essa afirmação

Para mim, isso faz sentido. Você executa uma consulta espacial = deve ter um índice espacial

Para mim, isso não faz sentido e acho que o SQL Server e o Postgis fazem um trabalho melhor ou pelo menos não o incomodam com os detalhes de desempenho. De fato, o SQL Server e o Postgis às vezes nem sequer usam o índice espacial (reverter para a verificação completa da tabela).

Para Oracle, você deve criar o índice e, portanto, preencher user_sdo_geom_metadata.

Apenas comparando isso com índices alfanuméricos, eles estão lá por razões de desempenho, sua instrução SQL deve funcionar com e sem ela.

Em um banco de dados Oracle, solte o índice e você obterá muitos erros e aplicativos que não poderão usar consultas espaciais e, portanto, não funcionarão.

user2192239
fonte