Quelles sont les implications des géométries invalides

15

J'ai importé des données dans une base de données Postgis et certaines géométries sont signalées comme non valides (ST_IsValidReason signale une auto-intersection ou une auto-intersection en anneau).

Les requêtes que j'effectue ne semblent pas affectées par l'aspect invalide de ces géométries (j'utilise uniquement des requêtes ST_Distance).

Quelles sont les choses qui se cassent lorsque les géométries ne sont pas valides?

La fixation de ces géométries "automatiquement" (buffer (geom, 0) ou ST_SimplifyPreserveTopology (geom, 0.0001)) est-elle une option?

diciu
la source

Réponses:

19

Conserver des données malformées est une mauvaise idée, car vous ne pouvez jamais prédire quand et où la panne se produira. De plus, des données malformées peuvent provoquer des Heisenbugs , le type de bugs le plus vicieux et illusoire.

Je pense qu'il est un peu inutile de discuter du résultat possible du stockage de géométries invalides. Cela dit, les conséquences peuvent inclure:

  • Mauvais résultats (c'est-à-dire, le ST_Distanceretourne des chiffres inexacts ou tout simplement faux)
  • Problèmes de performances de la base de données: la conservation de données mal formées peut sérieusement endommager les performances de la base de données et créer un énorme fichier journal, car chaque appel de fonction écrit une erreur dans le journal et perturbe le travail de base de données ordinaire.
  • La base de données plante.
  • L'application plante - soit causée par la réception de données malformées de la base de données, soit par la réception de résultats déraisonnables (distance négative, par exemple).
  • Comportement fantôme (voir lien ci-dessus). C'est la pire conséquence de toutes. Vous aurez des choses étranges qui se passent. Ralentissements, perte de données, plantages, résultats déraisonnables, longues pauses, aucune réactivité et bien d'autres malédictions. Vous pourriez ne pas être en mesure de les repérer ou de les reproduire, car ils relèvent tous de la catégorie "non définie" dans chaque documentation.

Mon conseil - si les petits tampons ne nuisent pas de manière significative à la cohérence de vos données, utilisez-les pour empêcher que ce qui précède ne se produise. Gardez vos données valides.

Adam Matan
la source
Pouvez-vous élaborer un peu sur l'utilisation de petits tampons? Comment je fais ça?
diciu
1
ST_Buffer(the_geom, 0.0000001)pourrait faire l'affaire pour l'auto-intersection. Utilisez-le uniquement si les conséquences d'une géométrie légèrement plus grande ne sont pas graves.
Adam Matan
1
D'après mon expérience, la correction de données malformées est une véritable enquête. Mais même si cela prend du temps, cela en vaut la peine. L' ST_Buffer(the_geom, 0.0000001)astuce aide certainement beaucoup.
Chau
Le problème est que ST_Buffer corrige la géométrie mais le résultat n'est pas vraiment ce à quoi je m'attendais - pour ce polygone invalide ici ( openstreetmap.org/browse/way/51954364 ) ST_Buffer ne renvoie que le rectangle en haut à gauche. ST_SimplifyPreserveTopology semble être plus proche de ce dont j'ai besoin (géométrie valide mais aussi proche que possible de l'original invalide). Des inconvénients dans l'utilisation de ST_SimplifyPreserveTopology?
diciu
Cette géométrie doit être traitée comme l'un MULTIPOLYGONdes deux polygones, pas comme un seul POLYGON. Essayez d'obtenir le WKT d'origine si possible.
Adam Matan
13

Vous pouvez empêcher les géométries non valides d'entrer dans votre base de données en premier lieu. Pour les utilisateurs de PostgreSQL / PostGIS, cela est simple à faire avec les contraintes de vérification . Par exemple, considérez une table public.my_valid_tableavec une colonne de géométries de polygone geom, utilisez le SQL / DDL suivant:

ALTER TABLE public.my_valid_table
  ADD CONSTRAINT enforce_valid_geom CHECK (st_isvalid(geom));

Remarque: cette table doit avoir des polygones valides avant d'appliquer la contrainte.

Si vous essayez ensuite d'insérer / ajouter une géométrie non valide, vous verrez une erreur:

ERROR:  new row for relation "my_valid_table" violates check constraint "enforce_valid_geom"
Mike T
la source