Editar: Pregunta de seguimiento aquí (= Encontrar polígonos de cabecera ).
¿Cómo puedo determinar el inicio de un río en PostGIS?
Tengo una red fluvial (Multiline) y quiero encontrar los puntos de inicio de los ríos.
Puedo seleccionar los puntos de inicio (rectángulos en el gráfico) utilizando
SELECT
ST_StartPoint(ST_LineMerge(a.geom)) as stp, a.gid AS gid
FROM
spatial.stream AS a
y de forma similar los puntos finales (cruces). Pero, ¿cómo puedo encontrar el inicio del río - no de los segmentos de la línea?
He intentado algo así como (encontrar los puntos de inicio, que no se cruzan con los puntos finales):
SELECT
ST_StartPoint(ST_LineMerge(a.geom)) as stp, a.gid AS gid
FROM
spatial.stream AS a, spatial.stream AS b
WHERE
ST_Disjoint(ST_StartPoint(ST_LineMerge(a.geom)), ST_EndPoint(ST_LineMerge(b.geom)))
Pero esto lleva una eternidad:
"Nested Loop (cost=0.00..1019343418.86 rows=525839789 width=323)"
" Join Filter: st_disjoint(st_startpoint(st_linemerge(a.geom)), st_endpoint(st_linemerge(b.geom)))"
" -> Seq Scan on stream_typ b (cost=0.00..4498.18 rows=39718 width=323)"
" -> Materialize (cost=0.00..6364.77 rows=39718 width=319)"
" -> Seq Scan on stream_typ a (cost=0.00..4498.18 rows=39718 width=319)"
Editar: No lo ejecuté hasta que terminó, por lo que incluso no sé si esta consulta devuelve el resultado deseado. Pero mirando las filas devueltas, esto no parece correcto (demasiado)).
Al final quiero encontrar los polígonos (grises en el gráfico) donde empieza un/un río (los polígonos verdes), pero no aquellos donde los ríos sólo pasan (el polígono rojo, sin inicios dentro). ¡Pero tener sólo los puntos de inicio sería un buen comienzo!
¿Alguna idea de cómo se puede hacer esto en PostGis? (también otras soluciones de código abierto como GRASS, R, etc. son bienvenidas).
Actualización : Mi idea de extraer sólo los puntos de inicio no era lo suficientemente concisa :( Por ejemplo, considere la siguiente situación:
Los polígonos verdes tienen ambos puntos de arranque (verdaderos) dentro y son los que quiero. El polígono rojo también tiene puntos de inicio dentro, pero el río fluye a través (así que no hay polígono de cabecera). Con la solución de John abajo obtengo ambos. Sólo quiero los arroyos de cabecera. No estoy seguro de si mi idea con los puntos de inicio llevará a la solución (me invento una nueva pregunta si lo deseo). He pensado en dos cláusulas Where:
- El polígono contiene un punto de inicio
- sin flujo de paso (= sólo 1 intersección del polígono con el arroyo).
He probado esto:
SELECT
polyg.*
FROM
polyg, start_points, stream
WHERE
st_contains(polyg.geom, start_points.geom)
AND ST_Npoints(ST_Intersection(poly.geom, stream.geom)) < 2
Pero nunca termina :( ¿Hay alguna forma mejor de consultar los polígonos de la cabecera?