【问题标题】:How to find the path along a line until it first intersects a polygon?如何找到沿线的路径,直到它首先与多边形相交?
【发布时间】:2019-10-27 01:29:51
【问题描述】:

我有一条路径作为与多边形相交的一系列有序点。我想在第一个多边形交点之前提取线的一部分。

我试图通过计算与多边形的差异来分割路径,但线也在其自相交处被分割(参见示例)。我需要从一开始一直提取路径的完整部分,直到它首先与多边形相交(示例中为蓝色正方形)。

# A wonky line that intersects itself   
l = sf::st_linestring(cbind(cos((0:100) * pi / 50), sin((0:100) * pi / 15 )))
# A polygon that intersects the line
p = sf::st_polygon(list(cbind(c(-.3, -.3, -.2, -.2, -.3), c(-.3, -.2, -.2, -.3, -.3))))

# Visualisation of the problem
plot(l)
plot(p, add = TRUE, col = "blue")

# Taking the first fragment of the difference does not work as the path intersects and divides itself
d = sf::st_difference(l, p)
plot(sf::st_linestring(d[[1]]), add = TRUE, col = "red")

在示例中,路径由所有交叉点(甚至在其自身)分割,因此路径的第一部分不会一直延伸到多边形。我怀疑 sf 包中有一个专门用于我目的的函数 - 但我还没有找到它。

【问题讨论】:

    标签: r sf


    【解决方案1】:

    一个自相交的线串不是“简单的”(参见st_is_simple(l)),即使它是“有效的”(参见st_is_valid(l)),sf 在这里为您提供了一个简单的功能。我们需要做的是使用简单的 LINESTRING 并重建更长的线特征......

    首先区分摆动线与多边形 - d 然后是多线串:

    > d = st_difference(l,p)
    

    如果我们将其转换为 sfc,然后将其转换为 LINESTRING,我们将获得不同 LINESTRING 几何形状的零件:

    > dl = st_cast(st_sfc(d),"LINESTRING")
    

    其中有 8 个:

    > length(dl)
    [1] 8
    

    那么从第一个开始,在我们碰到多边形之前我们需要跟随多少?让我们获取线段与多边形的交点 - 这是一个稀疏列表 - 如果没有交叉点,元素的长度为 0,如果有交叉点,则长度大于 0:

    > sint = st_intersects(dl,p)
    

    该列表不为零的第一个元素是命中多边形的第一行字符串:

    > min(which(lengths(sint)>0))
    [1] 3
    

    这意味着我们到多边形的线是前三个线串:

    > dl[1:3]
    Geometry set for 3 features 
    geometry type:  LINESTRING
    dimension:      XY
    bbox:           xmin: -0.220294 ymin: -0.9945219 xmax: 1 ymax: 0.9945219
    epsg (SRID):    NA
    proj4string:    NA
    LINESTRING (1 0, 0.9980267 0.2079117, 0.9921147...
    LINESTRING (0.9510565 0.8660254, 0.9297765 0.95...
    LINESTRING (0.309017 -0.8660254, 0.309017 -0.86...
    

    您可以将它们合并为一个特征并绘制:

    > plot(l)
    > plot(p,add=TRUE,col="red")
    > topoly = st_union(dl[1:3])
    > plot(topoly, add=TRUE, lwd=3)
    

    【讨论】:

    • 是的——这正是我所需要的。谢谢!这是第二步:将multilinestring 转换为linestrings 列表,这是至关重要的。作为sf 包的新手,为什么st_intersects 应该为multilinestringmultipoint 返回单个值是令人困惑的。多线几何和多线几何之间的区别完全消除了这一点。
    猜你喜欢
    • 2011-08-30
    • 1970-01-01
    • 1970-01-01
    • 2015-08-05
    • 1970-01-01
    • 1970-01-01
    • 2021-04-23
    • 1970-01-01
    • 2021-07-13
    相关资源
    最近更新 更多