2

我有几个多边形,它们实际上是点的联合。我想要一种相当快速的方法来删除不是陆地的点(但在河流、湖泊、海洋等)。

所以到目前为止,我已经想出了以下方法,它将我从左图带到右图:

在此处输入图像描述

import fiona
from shapely.geometry import Point, shape

# Shape files (Small Lakes Europe, Lakes, Coast)
le_loc = ".../water-polygons-split-4326/ne_10m_lakes_europe.shp"
lw_loc = ".../water-polygons-split-4326/ne_10m_lakes.shp"
c_loc = ".../water-polygons-split-4326/water_polygons.shp"

print("Opening Shape-Files")
le_poly = [shape(pol['geometry']) for pol in fiona.open(le_loc)]
lw_poly = [shape(pol['geometry']) for pol in fiona.open(lw_loc)]
c_poly = [shape(pol['geometry']) for pol in fiona.open(c_loc)]

def point_in_water(lat, lon):
    xy_point = Point(lon, lat) 
    for one in [c_poly, lw_poly, le_poly]:
        for shape in one:
            if shape.contains(xy_point):
                return True
    return False

# Test (true)
print(point_in_water(46.268408, 6.180437))

然后在一个循环中我测试我的观点:

with open(in_csv) as f:
    for x in csv.reader(f):
        # Lat, Lng, Mins, Mode
        if not point_in_water(float(x[0]), float(x[1])):
           coords.append([x[0], x[1])

我使用三个适合我的目的的形状文件(湖泊有点粗糙):海岸湖泊小湖

但是,对于 10,000 点,代码有点慢(我有大约 30 个文件,所以要检查 300,000 点)。

我想知道以下任何一项是否可能:

1) 我正在循环遍历形状并检查 shape.contains(point) 而不是遍历点并检查 point.within(shape) -> 我不确定是否会有改进?

2)使用空间索引可能会加快速度,但我认为 RTree 不再适用于 Python 3.4

3)也许有一个更快的功能(粗略的包含),它只检查边界,我可以将它用作第一步,然后包含作为步骤 2。

4)不是循环通过点,有没有办法一次矢量化和传递?

5)也许将形状优美的多边形转换为路径会更快,以便我可以使用matpotlib的path.contains_point?

6)最后,我意识到我可能应该使用墨卡托投影作为多边形测试中的点,但粗剪对我来说很好(它不像水形状文件那样超级准确)。

谢谢

4

0 回答 0