#1 Thu 23 January 2020 15:33
- ChristopheV
- Membre
- Lieu: Ajaccio
- Date d'inscription: 7 Sep 2005
- Messages: 3199
- Site web
Tuto comparer deux référentiels vecteurs avec postgis
Bonjour,
Problématique : j'ai deux référentiels topographiques de type vecteur, ici le parcellaire actuel (ensemble A) et le parcellaire napoléonien (Ensemble N).
J'ai géoréférencé sans déformation (transfo d'Helmert) l'ensemble N en me servant de A comme référence. Je constate que des arcs qui devraient être strictement égaux sont légèrement différents, jusque là normal. Comment déformer l'ensemble N pour le faire caler exactement avec A il existe de nombreuses méthodes, mais quelle que soit la méthode, il faut connaître le vecteur constitué par deux sommets homologues de A et N.
Etape 1 :
Création d'un buffer à partir des linestring de A. On cherche ensuite toutes les linestring de N qui sont strictement incluses dans un élément de A, on retient le couple idA et idN dans la table nommée ici "testedgeid"
Etape 2 :
Utilisation de la distance de Hausdorff pour comparer les éléments de A et de N pour chaque ligne de testedgeid
Code:
WITH p as (SELECT ida, idn, ST_HausdorffDistance(a.geom,n.geom) d, MIN(ST_HausdorffDistance(a.geom,n.geom)) OVER (PARTITION BY ida) mind, a.geom ag ,n.geom ng --INTO teshausdorff FROM testedgeid, toponapo.edge_data n, topo.edge_data a WHERE a.edge_id=ida AND n.edge_id=idn ORDER BY a.edge_id,n.edge_id ) SELECT * INTO teshausdorff8 FROM p WHERE d=mind AND mind<=2 ORDER BY ida,idn
Ceci permet de déterminer pour chaque élément de A l'élément de N compris dans le buffer qui est le plus semblable à l'élément de A.
On choisit ensuite de façon empirique la valeur "acceptable pour la comparaison des formes (ici 2)
3 Une fois les couples à comparer déterminés par les étapes précédentes, on transforme la LINESTRING en sommets, ce pour A, ce Pour N.
Puis on appaire les sommets de A et ceux de N en fonction de la distance mini. Chaque sommet de A est comparé à chaque sommet de N on retient le couple a,n tel que la distance a,n soit minimale. Puis on calcul le vecteur :
Code:
WITH p as (SELECT edge_id as ea, idn, geom FROM topo.edge_data,teshausdorff8 WHERE ida=edge_id ), p1 as (SELECT ea, st_dumppoints(geom) as d, geom as ag, idn FROM p), p2 as (SELECT ea,(d).path as ap,(d).geom as ga,ag, idn FROM p1), q as (SELECT edge_id en,geom ng, ida FROM toponapo.edge_data,teshausdorff8 WHERE idn=edge_id ), q1 as (SELECT en, st_dumppoints(ng) as d,ng,ida from q), q2 as (SELECT en,(d).path as np,(d).geom as gn,ng,ida FROM q1), K as (SELECT ida,idn,ap,np,st_distance(ga,gn) as d, min(st_distance(ga,gn)) OVER (PARTITION BY ida,idn,ga) mindp,ga,gn FROM p2,q2 WHERE idn=en AND ida=ea ORDER BY ea,idn,ap,np ) SELECT k.*, st_makeline(ga,gn) vg INTO testvec9 FROM k WHERE d=mindp
Réalisé à l'échelle d'une commune ça donne des résultats sympas. En jaune N en bleu A en rouge le vecteur de déformation.
Dernière modification par ChristopheV (Thu 23 January 2020 18:13)
Christophe
L'avantage d'être une île c'est d'être une terre topologiquement close
Hors ligne