모든 속성을 잃지 않고 빠른 방법으로 자체 분할 geopandas Linestring geodataframe
Nov 24 2020
많은 LineStrings의 geodataframe이 있습니다. 유도 선은 교차하지만 해당 교차점에서 분할되지 않습니다. 이것을 달성하기위한 나의 현재 해결책은 여기 에서 있다 :
network = gp.read_file(filenameNetwork)
newNetwork = gp.GeoDataFrame()
for splittedGeom in network.geometry.unary_union:
part = gp.GeoDataFrame([[splittedGeom]], columns=['geometry'])
newNetwork = newNetwork.append(part)
그러나이 솔루션으로 모든 컬럼을 풉니 다. 나는 또한 이것을 시도했지만 너무 오래 걸립니다.
from shapely import ops
streets = streets.reset_index(drop=True)
streets = streets[['geometry', 'costs']]
headers = list(streets.columns)
index = 0
newStreets = gp.GeoDataFrame( columns=['geometry'])
for line in range(len(streets)-1):
print(line, len(streets))
linegeom = streets.at[line, 'geometry']
isNotSplitted = True
for line2 in range(len(streets)):
if line2 == line:
continue
linegeom2 = streets.at[line2, 'geometry']
if linegeom2.crosses(linegeom):
try:
linegeomsplitted = ops.split(linegeom, linegeom2)
except:
continue
isNotSplitted = False
for split in range((len(list(linegeomsplitted.geoms)))):
splittedline = (list(linegeomsplitted.geoms))[split]
for head in headers:
if head == 'geometry':
headValue = splittedline
else:
headValue = streets.at[line, head]
newStreets.at[index, head] = headValue
index += 1
if isNotSplitted:
for head in headers:
headValue = streets.at[line, head]
newStreets.at[index, head] = headValue
index += 1
streets = newStreets
streets = streets.drop_duplicates(subset=['geometry'],
keep='first')
어떤 제안?
답변
4 gene Nov 30 2020 at 11:31
해결책을 찾았습니다.
내 예를 사용하여 :
a) 원본 shapefile

import geopandas as gpd
df = gpd.read_file("stac-graphe.shp")
df
id test geometry
1 test1 LINESTRING (10.244 -273.317, 784.201 -222.924)
2 test2 LINESTRING (210.484 -553.461, 324.991 -4.534)
3 test3 LINESTRING (169.970 -134.276, 126.511 -218.533...
4 test4 LINESTRING (100.000 -433.317, 724.390 -112.341...
5 test5 LINESTRING (232.683 -113.317, 694.146 -445.024...
6 test6 LINESTRING (563.415 -552.341, 559.512 -22.585)
b) 부동 산술 문제를 방지하기 위해 원래 지오메트리 버퍼링 ( intersects
또는에서 within
)
df2 = df.copy()
df2.geometry = df2.geometry.buffer(0.01)
c) unary_union
자체 교차 된 모든 유도 선을 분할하는 데 사용
un = df.geometry.unary_union
geom = [i for i in un]
id = [j for j in range(len(geom))]
unary = gpd.GeoDataFrame({"id":id,"geometry":geom})
unary.head()
id geometry
0 LINESTRING (10.244 -273.317, 192.920 -261.423)
1 LINESTRING (192.920 -261.423, 272.484 -256.242)
2 LINESTRING (272.484 -256.242, 418.308 -246.748)
3 LINESTRING (418.308 -246.748, 469.403 -243.421)
4 LINESTRING (469.403 -243.421, 561.095 -237.451)
d) 공간 조인 ( within
또는 사용)을 사용 intersect
하여 두 데이터 프레임을 조인하고 원래 속성을 검색합니다.
from geopandas.tools import sjoin
result =sjoin(unary, df2, how="inner",op='within')
result.head()
id_left geometry index_right id_right test
0 LINESTRING (10.244 -273.317, 192.920 -261.423) 0 1 test1
1 LINESTRING (192.920 -261.423, 272.484 -256.242) 0 1 test1
2 LINESTRING (272.484 -256.242, 418.308 -246.748) 0 1 test1
3 LINESTRING (418.308 -246.748, 469.403 -243.421) 0 1 test1
4 LINESTRING (469.403 -243.421, 561.095 -237.451) 0 1 test1

1 GevaertJoep Nov 28 2020 at 20:14
해결책은 아니지만 도움이 될 수 있습니다. 공용체의 교차를 만들려고하면 교차하는 각 속성에 대해 두 개의 반복 가능 항목이 제공됩니다. 그러나 일부 선 부분은 점이됩니다 ... :
원래:

산출:

아래 코드를 약간 수정하면 작동 할 수 있습니까?
import geopandas as gp
network = gp.read_file(filepath)
newNetwork = gp.GeoDataFrame()
geom = network.unary_union
newNetwork = gp.GeoDataFrame(columns=network.columns)
for i in range(len(network)):
for splittedGeom in network.intersection(network.unary_union)[i]:
part = gp.GeoDataFrame([list(network.loc[i,network.columns[:-1]])+[splittedGeom]],columns=list(network.columns))
newNetwork = newNetwork.append(part)
newNetwork.plot()