Punkt-IDs den jeweiligen Start- und Endattributen der Polylinie zuweisen?

9

Ich habe zwei Shapefiles, Point und Polyline. Ich versuche, meine Polylinienebene mit der Punktdaten-ID (systemID) zu füllen, an der die Linien dort beginnen, wo sie enden. z.B. Erstellen Sie zwei Spalten (von und bis). Den Leitungen ist bereits die Durchflussrichtung zugeordnet. Ich verwende ArcHydro-Tools, aber Arcpy ist auch in Ordnung.

In ArcHydro habe ich versucht, Attributwerkzeuge> Von / Bis-Knoten für Linien generieren zu verwenden, aber es werden Werte für An und Von erstellt, die nicht aus meinen Punktdaten stammen. Meine andere Alternative bestand darin, Feature to Vertices zu verwenden und das Ergebnis mit meiner Punktdatentabelle zu verknüpfen, um die System-ID zu erhalten. Aber dann müsste ich auch die Polylinienebene aktualisieren. Ich bin sicher, es gibt einen einfacheren Weg, dies zu tun.

Hinweis: Nicht alle Linien haben Punkte an den Eckpunkten. Leere Werte sind für sie in Ordnung.

JrUser
quelle
Ihre Punkte haben also ein Feld 'systemID', das in FNode, TNode-Felder in den Polylinien gehen muss ... ist das richtig?
Michael Stimson
Irgendwo hier gibt es eine Frage wie diese mit einer Antwort, bei der es sich im Grunde genommen um einen Anfang und ein Ende von Linie zu Punkt als separate Feature-Classes handelt. Schneiden Sie die beiden (einzeln) mit Ihren Punktdaten, um die IDs zu erhalten, und verbinden Sie sie dann räumlich mit den Linien mithilfe der Linie ID und Zuordnung zum richtigen Start- oder Endfeld (möglicherweise wird dort ein Feld berechnet). Ich kann es momentan allerdings nicht finden. Ich habe es gefunden, als ich nach diesem gesucht habe .
Chris W
Hier ist es: gis.stackexchange.com/questions/85082 Und es war Feature Vertices zu Punkten, nicht Linie oder Features zu Punkten. So ziemlich das, was Sie am Ende der Frage erwähnen.
Chris W
@ ChrisW, ich mag die Antwort von FelixIP wirklich sehr . Es sind nur zwei Attributverknüpfungen.
Michael Stimson

Antworten:

12

Manchmal ist es besser, keine Out-of-the-Box-Lösung zu verwenden. Deshalb schlage ich vor

  1. Füllen Sie X- und Y-Felder in der Knotenebene aus und konvertieren Sie sie in Ganzzahlen, z. B. cm. Erstellen Sie ein Zeichenfolgenfeld und füllen Sie es aus, indem Sie Zeichenfolgenrepräsentationen von Ganzzahlen verketten.
  2. Machen Sie ähnliche Schritte in der Verknüpfungstabelle für den ersten Punkt in der Form.
  3. Verbinden Sie die Knotentabelle mithilfe der zuletzt erstellten Felder mit Links und übertragen Sie die Knoten-ID in das FROM-Feld.

Gehe zu 2, aber benutze den letzten Punkt, um TO nodeID zuzuweisen

FelixIP
quelle
Mag ich! Feld berechnen so etwas wie str (rund (! Form! .FirstPoint.X, 3)) + "," + str (rund (! Form! .FirstPoint.Y, 3)) (Python-Parser) für von Knoten, str (rund (! Shape! .LastPoint.X, 3)) + "," + str (rund (! Shape! .LastPoint.Y, 3)) für den Knoten, dann ähnlich dem Punkt (als Text), dann verbinden ... Hervorragende Art der räumlichen Verbindung ohne den Schmerz Felix! Runde auf wichtigere Ziffern für geografische Daten (wie 7 oder 8).
Michael Stimson
Sehr schnell auch in einer Skriptumgebung, in der das Wörterbuch natürlich die langsame Tabellenverknüpfung ersetzt
FelixIP
Int (X * 100), wenn sie in metres projiziert werden. Verwenden Sie alternativ Michaels Code
FelixIP
Auf jeden Fall einfacher als die Methode in der Frage, auf die ich oben verwiesen habe. Weniger Schritte, weniger Tools und keine Einschränkungen der Lizenzstufe. Interessante Idee, einen räumlichen Join in einen regulären Attribut-Join umzuwandeln.
Chris W
1

Ich habe vor ein paar Monaten genau das Gleiche getan. Ich habe arcpy verwendet, aber das Skript ist viel zu lang, um hier veröffentlicht zu werden, sodass ich Ihnen einen Überblick darüber geben werde, was ich getan habe.

  1. Ich habe eine räumliche Verknüpfung verwendet, um festzustellen, welche Punkte / Knoten innerhalb eines bestimmten Linienmerkmals liegen.

  2. Da die räumliche Verbindung die Flussrichtung nicht berücksichtigt, habe ich arcpy verwendet, um festzustellen, welcher der Startpunkt und welcher der Endpunkt war. Ich konnte dies tun, indem ich die Funktion arcpy description verwendete, um Koordinateninformationen für die Start- / Endscheitelpunkte des Linien-Features zu extrahieren und diese mit den Koordinatenwerten der verbundenen Punkte zu vergleichen.

  3. Nachdem ich herausgefunden hatte, welche der An / Von-Punkte welche waren, verwendete ich die Funktion setValue, um die An / Von-Felder im ursprünglichen Polylinien-Dataset zu füllen.

Natürlich steckt noch ein bisschen mehr dahinter, aber ich habe die wichtigsten Punkte skizziert.

Geord359
quelle
In meinem geometrischen Netzwerk kann die Strömungsrichtung in eine der Hauptrichtungen sein. Ich konnte unmöglich eine Flussrichtung aus dem Vergleich der Rohkoordinaten ermitteln, wenn ich nicht auch ein Flussrichtungsraster oder etwas Äquivalentes verwendete. Auch das kann problematisch sein, da Rohre manchmal gegen die natürlichen Konturen geneigt sind oder Wasser bergauf gepumpt wird. Wie können Sie sicher sein, dass Ihre Strömungsrichtung korrekt ist?
Priscilla
1

Ich war von @FelixIP inspiriert, wollte aber eine Lösung ohne Joins oder die Erstellung zusätzlicher Dateien schreiben, da mein Netzwerk mit 400K + Pipes und 500K + Knoten ziemlich groß ist.

Der geometrische Netzwerkaufbau erzwingt, dass X, Y der Knoten und der Rohrenden zusammenfallen. Sie können auf diese Positionen mit den Form-Token in bogenförmigen Cursorn zugreifen und sie abgleichen. Die Form-Token für Linien geben ein Array der Scheitelpunkte in der Reihenfolge zurück, in der sie gezeichnet wurden. In meinem Netzwerk ist die Ziehreihenfolge der Rohre stark von der Qualitätssicherung abhängig, da wir hiermit die Durchflussrichtungen festlegen. Der erste Scheitelpunkt ist also der Anfang der Pipe, und der letzte Scheitelpunkt ist das Ende der Pipe.

Referenz: ASSETID = ID der Pipe, UNITID = Knoten-ID am Anfang der Pipe, UNITID2 = Knoten-ID am Ende der Pipe.

nodes = "mergeNodes"
pipes = "SEWER_1"

nodeDict = {}
pipeDict = {}

#populate node dictionary with X,Y as the key and node ID as the value
for node in arcpy.da.SearchCursor(nodes, ["UNITID", "SHAPE@XY"]):
    nodeDict[(node[1][0], node[1][1])] = node[0]

#populate pipe dictionary with pipe ID as the key and list of X,Y as values 
#vertices populated in the order that the line was draw
#so that [0] is the first vertex and [-1] is the final vertex
for pipe in arcpy.da.SearchCursor(pipes, ["ASSETID", "SHAPE@"]):
    for arrayOb in pipe[1]:
        for point in arrayOb:
            if pipe[0] in pipeDict:
                pipeDict[pipe[0]].append((point.X, point.Y))
            else: 
                pipeDict[pipe[0]] = [(point.X, point.Y)]

#populate UNITID with the first vertex of the line
#populate UNITID2 with the final vertex of the line
with arcpy.da.UpdateCursor(pipes, ["ASSETID", "UNITID", "UNITID2"]) as cur:
    for pipe in cur:
        if pipeDict[pipe[0]][0] in nodeDict:
            pipe[1] = nodeDict[pipeDict[pipe[0]][0]]
        if pipeDict[pipe[0]][-1] in nodeDict:
            pipe[2] = nodeDict[pipeDict[pipe[0]][-1]]
        cur.updateRow(pipe)
Priscilla
quelle
Dies sind 90% meiner Arbeit, aber ich gehe nicht zweimal durch Pipes, da das Knotenwörterbuch bereits verfügbar ist.
FelixIP