¿Cómo usar ST_Intersection?

15

Aquí hay un resumen rápido sobre lo que estoy tratando de hacer: tengo 3 tablas en Postgres, 'a' y 'b', cada una tiene una columna Polígono y 'c' tiene una columna Punto. Lo que estoy tratando de hacer aquí es obtener las intersecciones de geometrías entre 'a', 'b' y 'c', y mostrar esas geometrías en una capa vectorial de OpenLayers.

Ya sé cómo mostrar cualquier tipo de geometría de una Cadena en OpenLayers, pero tengo problemas con la función ST_Intersection de PostGIS, estoy haciendo esto:

SELECT ST_Intersection(a.geom, b.geom) as inter from a, b;

donde a.geom y b.geom son las dos columnas de geometría, y recibo este mensaje de error:

NOTICE:  TopologyException: found non-noded intersection between 515172 2.14408e+06, 497067 2.13373e+06 and 501321 2.13546e+06, 471202 2.14843e+06 500621 2.13576e+06 
ERROR:  GEOS Intersection() threw an error!

También intenté expresar la geometría resultante como texto usando ST_AsText así:

SELECT ST_AsText(ST_Intersection(a.geom, b.geom)) as inter from a, b;

pero me envía este mensaje de error:

HINT: No function matches the given name and argument types. You might need to add explicit type casts.

No sé qué estoy haciendo mal, solo quiero que el WKT de los polígonos lo muestre en OpenLayers, así es como visualizo una geometría de un WKT:

                    var in_options = {
                        'internalProjection': new OpenLayers.Projection("EPSG:4326"),
                        'externalProjection': new OpenLayers.Projection("EPSG:4326")
                    }; 

                    var fea= new OpenLayers.Format.WKT(in_options).read(data); //data is the string with the WKT
                    vectorLayer.addFeatures([fea]); //this piece of code works great
                    map.zoomToExtent(bounds);

ACTUALIZACIÓN: probé el siguiente:

SELECT ST_Intersection(a.geom, b.geom) as intersect_ab FROM a INNER JOIN b ON 
ST_Intersection(a,b) WHERE ST_Overlaps(a.geom, b.geom) 
AND ST_isvalid(a.geom)='t' AND ST_isvalid(b.geom)='t';

pero recibo el siguiente mensaje de error:

ERROR: Function st_intersection(a,b) does not exist.
HINT: No function matches the given name and argument types. You might need to add explicit type casts.

Agregué el válido para verificar que solo se están evaluando polígonos válidos, pero indica que el error está en la intersección ST_ (Intersección, a, b), tanto a, byc tienen el mismo SRID, así que estoy realmente confundido, lo siento si estoy preguntando demasiado, pero soy bastante nuevo con PostGIS, así que espero no molestarte mucho. Gracias.

Uriel
fuente
1
¿Qué SELECT PostGIS_Full_Version();devuelve?
Mike T
POSTGIS = "1.4.0" GEOS = "3.1.0-CAPI-1.5.0" PROJ = "Rel. 4.7.1, 23 de septiembre de 2009" USE_STATS
Uriel

Respuestas:

8

Supongo que fallará si la intersección devuelve NULL. Por lo tanto, debe agregar una cláusula where para verificar si realmente hay una intersección antes de intentar crear el WKT.

bajo oscuro
fuente
Intenté esto: SELECCIONAR ST_Intersection (a.geom, b.geom) como intersect_ab DESDE a INNER JOIN b ON ST_Intersection (a, b) WHERE ST_Overlaps (a.geom, b.geom) AND ST_isvalid (a.geom) = 't 'AND ST_isvalid (b.geom) =' t '; pero devolvió el mismo error: ** ERROR: la función st_intersection (a, b) no existe. SUGERENCIA: Ninguna función coincide con el nombre dado y los tipos de argumento. Es posible que deba agregar conversiones de tipo explícito. ** Estoy realmente atrapado en este caso, si me pueden ayudar realmente lo apreciaré.
Uriel
Pruebe el resumen (a.geom) y el resumen (b.geom) para investigar los valores.
oscuro
resumen -------------------------- Polígono [BS] con 1 anillo anillo 0 tiene 4 puntos Polígono [BS] con 1 anillo anillo 0 tiene 5 puntos puntos Polígono [BS] con 1 anillo anillo 0 tiene 10 puntos
Uriel
Sí, debería ser ST_Intersection (a.geom, b.geom) no ST_Intersection (a, b)
underdark
6

La pista es

ERROR: Function st_intersection(a,b) does not exist.
HINT: No function matches the given name and argument types. You might need to add explicit type casts.

Como dice el mensaje de error, no puede usar st_intersection de esa manera. Resumiendo las otras respuestas, debe usar algo como esto:

SELECT ST_Intersection(a.geom, b.geom) as intersect_ab 
FROM a INNER JOIN b ON ST_Intersects(a.geom,b.geom)
WHERE ST_isvalid(a.geom)='t' AND ST_isvalid(b.geom)='t';

AFAIK no tiene sentido usar st_overlaps y st_intersects en la misma oración, ya que son bastante similares .

Francisco Puga
fuente
4

Probé entre diferentes capas de polígonos y falló si hay al menos una geometría no válida en una de las capas. ¿Verificó la validez de sus polígonos usando ST_isvalid (the_geom)? Puede ser la clave.

Fabien Ancelin
fuente
Intenté esto: SELECCIONAR ST_Intersection (a.geom, b.geom) como intersect_ab DESDE a INNER JOIN b ON ST_Intersection (a, b) WHERE ST_Overlaps (a.geom, b.geom) AND ST_isvalid (a.geom) = 't 'AND ST_isvalid (b.geom) =' t '; pero devolvió el mismo error: ** ERROR: la función st_intersection (a, b) no existe. SUGERENCIA: Ninguna función coincide con el nombre dado y los tipos de argumento. Es posible que deba agregar conversiones de tipo explícito. ** Estoy realmente perdido en cuanto a por qué no funciona
Uriel
2

Intenta algo como esto:

SELECT  ST_Intersection(a.geom, b.geom) As intersect_ab
    FROM a INNER JOIN b ON ST_Intersection(a,b)
    WHERE ST_Overlaps(a.geom, b.geom)
    ;

Fuente

CaptDragon
fuente
Intenté eso también pero devuelve el mismo mensaje de error: SUGERENCIA: Ninguna función coincide con el nombre dado y los tipos de argumento. Es posible que deba agregar conversiones de tipo explícito.
Uriel
¿Qué tal si usa "INNER JOIN b ON ST_Intersection (a.geom, b.geom)"?
CaptDragon
Dice: ERROR: el argumento de JOIN / ON debe ser de tipo booleano, no de tipo geometría.
Uriel
shizer ... debe haber algo mal con los datos o algo porque este tipo de consulta funciona para mí.
CaptDragon
Agregué AND ST_isvalid (a.geom) = 't' AND ST_isvalid (b.geom) = 't'; al final sólo para evaluar las geometrías válidos pero me está diciendo que el error está en que ST_Intersection (a, b)
Uriel
1

Traté de excluir las geometrías inválidas pero no funcionó, así que al final tuve que eliminar todas las geometrías inválidas y luego usar esto:

SELECT ST_AsText(ST_Intersection(a.geom, b.geom)) as intersect_ab FROM a,b 
WHERE ST_Overlaps(a.geom, b.geom) AND ST_isvalid(a.geom)='t' AND ST_isvalid(b.geom)='t';

Como puede ver, omití la parte ST_Intersection (a, b), y funcionó muy bien, estoy un poco triste porque no pude encontrar una manera de excluir cualquier geometría no válida de mi selección, de todos modos gracias a todos por ayudarme aquí afuera.

Uriel
fuente
0

Tuve este problema una vez.

<pre>NOTICE:  TopologyException: found non-noded intersection between xxx, xxxx and xxx, xxx  ERROR:  GEOS Intersection() threw an error!</pre>

Pude resolver este error usando este método.
- Use QGIS
- Agregue una capa vectorial de su base de datos
- Tome el punto del mensaje de error y búsquelo en QGIS
   "QuickWKT" (complemento) se puede usar para encontrarlo
- Luego verá la cadena lineal problemática
- Active el modo de edición
- Seleccione "herramienta de nodo" para mostrar el nodo verde (problema de nodo)
- Aleje el nodo del nodo superpuesto
- Guarde los cambios

Ruthe
fuente