異なる長さのセグメントの一致


13

私は、小さなセグメントと、それらが最も関連している可能性が高い大きなセグメントとを一致させようと試みています。

これが私が持っているデータの典型的な例です:

セグメント

ここでは、セグメント652を198969に一致させる必要がありますが、711および707は何にも一致しません。

さまざまな方法、特にハウスドルフ距離(ここの回答に基づいて)を探しました。PostGISを使用して計算しましたが、奇妙な結果が得られます:最短距離は707と198985の間であり、652はたとえば198985よりも198969までの距離が大きいです(必要に応じてクエリと結果を追加できます)。

Hausdorffは実際にこれを解決する正しい方法ですか?他のアプローチはありますか?言及したパラメーター(距離、方位など)の一連のチェックを作成することを考えましたが、エッジケースまたはそれらがどれだけしきい値に達しているかなどを処理するために条件の束をすべて追加する必要があります向かい合っています。

更新:許容できる妥協案と思われる方法を見つけました:

  • 最初に<->、10メートル以内にある(PostGIS オペレーターを使用して)一致させようとしている青いセグメントから最も近い10個の黒いセグメントを見つけます。
  • 次に、それぞれの黒いセグメントの青いセグメントの端に最も近い点を見つけて(を使用してST_ClosestPoint)新しいセグメントを作成し、長さが青いセグメントの90%未満の結果を除外します(セグメントはそうではありません)直面している、またはベアリングの差が〜20°以上であること)
  • 次に、距離とハウスドルフ距離がある場合、ソートされた最初の結果を取得します。

微調整を行う必要があるかもしれませんが、今のところ許容できる仕事をしているようです。いくつかのエッジケースを見逃した場合に実行する他の方法や追加のチェックを探しています。


1
(青)セグメントのエンドポイントを使用して、ターゲット(黒)セグメント間の潜在的な一致を特定しないのはなぜですか?探しているセグメントの一致は、両方のエンドポイントが共通のターゲット(実行する簡単なクエリ)に近いときに発生します。この方法は、セグメントエンドポイントの位置のエラーに起因する不一致を処理します。エラーが発生すると、対処が困難になる可能性があります。
whuber

1
うん、私は実際にこれらの線に沿って何かを試しています、詳細で質問を更新します。
ジュクルパ

1
私はあなたを正しく理解しているかどうかはわかりませんが、青い線の重心を作成し、それらから最も近い線までの距離を確認して、結果として最短距離を残そうとしましたか?
シリル

1
こんにちはCyril、私はもうこの問題に取り組んでいませんが、問題は、青のセグメントをその向きに基づいて一致させ、黒のセグメントにどれだけ「向いている」かということでもありました。つまり、この場合、711は黒のセグメントにかなり近いにもかかわらず、711とは一致しないはずです。
1

回答:


1

以下に、私が書いたいくつかの機能を示します。ポリラインがラインを爆発させる場合、ラインがポリラインまたはセグメントであるかどうかを確認し、ラインの最初のポイントと最後のポイントの方位角と逆数を比較し、コードの許容基準を設定して決定します。これらはarcpyメソッドですが、変更することができます。

線分ESRI @shapeから方位角を返します

def returnAzimuth(shape):
    point1 = shape.firstPoint
    point2 = shape.lastPoint
    dX = point2.X-point1.X
    dY = point2.Y-point1.Y
    az = math.atan2(dX,dY)*180/math.pi
    if az<0:
        az = az+360
        return az
    return az

ESRIポイントから逆を返します

def returnInverse(point1,point2):
    dX = point2.X-point1.X
    dY = point2.Y-point1.Y
    dis = sqrt(dX**2+dY**2)
    az = math.atan2(dX,dY)*180/math.pi
    if az<0:
        az = az+360
        return az,dis
    return az,dis

ポリラインを線分に分解する

def explodePolyline(shape):
    sr = "insert your spatial reference"
    lines=[]
    pnts = shape.getPart(0)
    for x in range(len(pnts)-1):
        array = arcpy.Array()
        point1 = arcpy.Point(pnts.getObject(x).X,pnts.getObject(x).Y,pnts.getObject(x).Z)
        point2 = arcpy.Point(pnts.getObject(x+1).X,pnts.getObject(x+1).Y,pnts.getObject(x+1).Z)
        array.add(point1)
        array.add(point2)
        line = arcpy.Polyline(array,sr,True,True)
        print(line)
        lines.append(line)
    return lines

このようにテーブルを駆け抜ける

for shape in Table:
    for shape2 in Table:
         check if shape is polyline:
            if yes, explode and compare returned line segments with shape2
                for seg in returnedlinesegments
                    if seg.firstpoint=shape2.lastpoint and shape.az=shape2.az
                        do stuff.....
            if no, compare shape and shape2
                if shape.firstpoint=shape2.lastpoint and shape.az=shape2.az
                   do stuff.....

これらのプロパティはpostgis-firstpoint、lastpoint、pointarrayで利用できるはずです。これは私が最もよく知っているものですが、上記はesriのプロパティであると想定しています。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.