Extrahieren Sie Punkte / Koordinaten aus einem Polygon in Shapely


72

Wie erhält / extrahiert man die Punkte, die ein shapelyPolygon definieren ? Vielen Dank!

Beispiel eines formschönen Polygons

from shapely.geometry import Polygon

# Create polygon from lists of points
x = [list of x vals]
y = [list of y vals]

polygon = Polygon(x,y)

Antworten:


79

Also entdeckte ich, dass der Trick darin besteht, eine Kombination der PolygonKlassenmethoden zu verwenden, um dies zu erreichen.

Wenn Sie geodätische Koordinaten wünschen, müssen Sie diese wieder in WGS84 umwandeln (via pyproj, matplotlib's basemapoder so).

from shapely.geometry import Polygon

#Create polygon from lists of points
x = [list of x vals]
y = [list of y vals]

some_poly = Polygon(x,y)

# Extract the point values that define the perimeter of the polygon
x, y = some_poly.exterior.coords.xy

33

Es hat eine Weile gedauert, bis ich herausgefunden habe, dass ein Polygon eine Außengrenze und möglicherweise mehrere Innengrenzen hat. Ich poste hier, weil einige der Antworten diese Unterscheidung nicht widerspiegeln, obwohl der ursprüngliche Beitrag fairerweise kein Polygon mit inneren Grenzen als Beispiel verwendet hat.

Die Punkte, die die Außengrenze bilden, sind in einer Koordinatenfolge angeordnet, die als erhalten werden kann

polygon.exterior.coords

Sie können die Länge dieses Objekts mithilfe von ermitteln len(polygon.exterior.coords) und das Objekt wie eine Liste indizieren. Verwenden Sie zum Beispiel, um den ersten Scheitelpunkt zu erhalten polygon.exterior.coords[0]. Beachten Sie, dass der erste und der letzte Punkt gleich sind. Wenn Sie eine Liste mit den Eckpunkten ohne diesen wiederholten Punkt wünschen, verwenden Sie polygon.exterior.coords[:-1].

Sie können die CoordinateSequence (einschließlich des wiederholten Scheitelpunkts) in eine Liste von Punkten konvertieren:

list(polygon.exterior.coords)

In ähnlicher Weise wird die Koordinatenfolge, die aus den Eckpunkten besteht, die die erste innere Grenze bilden, als erhalten polygon.interiors[0].coords, und die Liste dieser Eckpunkte (ohne den wiederholten Punkt) wird als erhalten polygon.interiors[0].coords[:-1].


Wie würden Sie alle Koordinaten erhalten, die vom Polygon begrenzt werden? Gibt es also Punkte im Polygon, wie man diese Koordinaten erhält?
Will.Evo

23

Sie können die formschöne mappingFunktion verwenden:

>>> from shapely.geometry import Polygon, mapping
>>> sh_polygon = Polygon(((0,0), (1,1), (0,1)))
>>> mapping(sh_polygon)
{'type': 'Polygon', 'coordinates': (((0.0, 0.0), (1.0, 1.0), (0.0, 1.0), (0.0, 0.0)),)}

2
Nett. Dies ist schön, da es eine einfache Verallgemeinerung einer Routine ermöglichen würde, die dies erfordert.
Ryanjdillon

6

Ich habe das benutzt:

list(zip(*p.exterior.coords.xy))

Polygon erstellt mit: gibt p = Polygon([(0,0),(1,1),(1,0),(0,0)])zurück:

[(0.0, 0.0), (1.0, 1.0), (1.0, 0.0), (0.0, 0.0)]

3

Wenn Sie wirklich die wohlgeformten wollen Punktobjekte , die das Polygon bilden, und zwar nicht nur Tupel von Koordinaten, können Sie , dass auf diese Weise tun:

points = MultiPoint(polygon.boundary.coords)

2

Mit NumPy.array können Sie ein formschönes Polygon in ein NumPy-Array konvertieren. Ich finde die Verwendung von NumPy-Arrays nützlicher als die von coords.xy zurückgegebenen Arrays, da die Koordinaten gepaart sind und nicht in zwei eindimensionalen Arrays. Verwenden Sie das, was für Ihre Anwendung nützlicher ist.

import numpy as np
x = [1, 2, 3, 4]
y = [9, 8, 7, 6]
polygon = Polygon(x,y)
points = np.array(polygon)

# points is:
[[ 1 9]
 [ 2 8]
 [ 3 7]
 [ 4 6]]

Gute Idee. Vielen Dank! Ich glaube, ich habe dies verwendet, als ich eine ungeordnete Gruppe von Punkten hatte, und mit coords.xydieser konnte ich eine geordnete Liste externer Punkte oder vielleicht die externen Punkte eines Gitters herausziehen ... Ich werde damit spielen wenn ich Zeit habe und mich wieder melde :)
Ryanjdillon

12
Der obige Code funktioniert nicht mit Shapely = 1.5.13 = py35_0. Polygon(x,y)wird nicht akzeptiert. np.array(some_actual_polygon)verhält sich auch nicht wie gezeigt.
Masterfool

2

Sie können eine der beiden folgenden Methoden verwenden.

1)

p = Polygon([(1,0),(1,1),(0,1),(0,0)])
for x,y in p.exterior.coords:
   print(x,y)

Der obige Code gibt Folgendes aus. Beachten Sie, dass (1,0) zweimal gedruckt wird, da external.coords eine geordnete Sequenz zurückgibt, die das Polygon vervollständigt.

1.0 0.0
1.0 1.0
0.0 1.0
0.0 0.0
1.0 0.0

2)

p.exterior.coords.xy

Es wird Folgendes ausgegeben

(array('d', [1.0, 1.0, 0.0, 0.0, 1.0]), array('d', [0.0, 1.0, 1.0, 0.0, 0.0]))

1
Diese beiden Methoden sind die gleichen und die gleichen wie meine Antwort vom 09.12.2013.
Ryanjdillon

@ryanjdillon ja der zweite ist der gleiche wie deins. Der erste, den ich fand, ist eine intuitivere Möglichkeit, die xy-Paare auszupacken.
Roomba

1
Die Frage war, wie man die Koordinaten erhält und nicht wie man Tupel auspackt. Ich antworte darauf, weil diese Antwort keine zusätzlichen Informationen zum Erhalten der Koordinaten hinzufügt und es nicht die erste ist, die eine bereits vorhandene Antwort wie diese wiederholt . Ihr Vorschlag wird am besten in Form eines Kommentars zu einer vorhandenen Antwort gemacht. Antworten wie diese verursachen unnötige Probleme, damit die Leute die kritischen Informationen finden können.
Ryanjdillon

1

Update (09.06.2017):

Da die letzte Antwort mit der neuesten Version von Shapely nicht mehr zu funktionieren scheint, schlage ich dieses Update vor.

Shapely bietet die Numpy-Array-Schnittstelle (wie im Dokument angegeben: http://toblerity.org/shapely/project.html )

Sei polyalso eine formschöne Polygongeometrie:

In [2]: type(poly)
Out[2]: shapely.geometry.polygon.Polygon

Dieser Befehl führt die Konvertierung in ein Numpy-Array durch:

In [3]: coordinates_array = np.asarray(poly.exterior.coords)

Hinweis:
Für ein Polygon müssen die äußeren Koordinaten angegeben werden, da die Angabe der direkten Geometrie ebenfalls nicht zu funktionieren scheint:

In [4]: coordinates_array = np.asarray(poly)
Out[4]: array(<shapely.geometry.polygon.Polygon object at 0x7f627559c510>, dtype=object)    
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.