Atualmente, estou trabalhando no campo de isócronas e nos algoritmos subjacentes. O que agora causa problemas não é o cálculo da própria isócrona, mas a visualização dos resultados.
O resultado do meu algoritmo de isócrona são pontos e arestas. Na verdade, eu tenho uma solução funcional, mas para 3873 bordas e para 1529 nós as coisas parecem durar uma eternidade (cerca de 2,0 segundos no meu laptop Lenovo T440s, que contém uma CPU Core i7 2015 e um SSD bastante rápido). Em vez de segundos, quero algo mais como msec :-).
Talvez alguém possa me ajudar a reduzir o tempo de cálculo necessário para construir os polígonos que visualizam as áreas acessíveis.
Mas espere ... as primeiras coisas primeiro!
Aqui está uma visualização das arestas que são o resultado do cálculo da minha isócrona:
essas arestas são armazenadas em uma tabela de banco de dados PostGIS e são cadeias de linhas simples.
O que quero mostrar ao usuário é o seguinte: Observe as áreas desconectadas no sul e leste da imagem. Elas devem ser desenhadas como áreas separadas (portanto, nenhuma fusão é permitida aqui :-))
Atualmente, estou usando esta consulta:
SELECT ST_AsGeoJson(St_Transform(ST_Multi(ST_Collect(polygons)), 4326)) AS coverage FROM (
SELECT ST_MakePolygon(ST_ExteriorRing(ST_GeometryN(segments, generate_series(1, ST_NumGeometries(segments))))) AS polygons FROM (
SELECT ST_Union(ST_Buffer("GEOMETRY", 20, 'quad_segs=2')) AS segments FROM my_edges AS a
) AS b
) AS c
Eu já fiz algumas experiências e também li muita documentação, mas simplesmente não consigo encontrar uma solução melhor.
A meu ver, o grande problema é o uso do ST_Union (conforme declarado nos documentos, essa função pode ser lenta). O mais interessante é que substituí-lo por ST_Collect parece desacelerar o cálculo ST_Buffer para que a consulta a seguir leve mais tempo, embora não preencha as áreas entre as bordas (apenas cria um buffer ao redor das linhas ):
SELECT ST_AsGeoJson(St_Transform(ST_Multi(ST_Collect(polygons)), 4326)) AS coverage FROM (
SELECT ST_Buffer(ST_Collect(ST_LineMerge("GEOMETRY")), 20, 'quad_segs=2') AS polygons FROM my_edges AS a
) AS b
Isso leva cerca de 3,8 segundos no meu sistema (quase o dobro do tempo). Minha primeira conclusão dessa pequena referência é que ST_Buffer fica inesperadamente lento quando se trata de MultiLineStrings (ainda mais lento do que ao criar buffers para cada linha e mesclar os buffers - o que aos meus olhos é estranho)
Também tentei usar formas alfa (usando a implementação de pgRouting), mas como não há valor alfa a ser definido (e, na verdade, não seria agora a que valor definir esse valor), apenas recebo um ótimo polígono ( então eu perderia as regiões no sul e leste como regiões separadas, e não é isso que eu quero).
O ST_Polygonize (que foi a primeira coisa que me veio à cabeça) não produziu nenhum resultado utilizável, mas talvez eu tenha perdido algo aqui ...
Existe uma maneira melhor de criar a área mostrada no PostGIS? Talvez também usando o código java (jts) ou o código javascript do lado do cliente (jsts)? Na verdade, eu poderia perder alguns detalhes, desde que as áreas mostradas em meu resultado permaneçam separadas e o cálculo fique (muito) mais rápido.