多边形是否有开放边?考虑 R {spdep} 中的 full/partial 个邻居

Has polygon have an open edge? Consider full/partial neighbors in R {spdep}

我想知道如何定义多边形是否有开放边。我认为如果多边形完全被邻居包围,它就没有开放的边缘。

使用 wonderful poly2nb(fc) 我得到了邻居列表:但是,从这个列表中,我不知道小区必须有多少个邻居才能完全被邻居包围?这是情况:

我的中心 red 多边形在这两种情况下都有 3 个邻居,但有开放边缘(左)或完全被邻居包围(右)。如果使用 raster 格式和 queen case,完全包围的单元格需要 8 个邻居。如果较小,则为开孔。但是,我可以从 poly2nb(fc)nb 对象中得到类似的东西吗?当然,我的数据可能包含单个多边形之间的条带和间隙,因此我不想完全依赖重叠边或其他东西。

我的真实数据在 dropbox or googleDrive

和计算邻居数量的r代码示例:

setwd("U:/Desktop/raw/myDir")

# Read input forest stand data
forest_fc = readOGR(getwd(), 
                    layer = "forest_fc")

# continuity based neighbourhood: 
# import whole 
# shapefile, do not split it by one feature at time
nb <- poly2nb(forest_fc, 
              #row.names = forest_fc,
              snap = 0) # snap to correct for the gaps/slivers 

# store the number of neighbours by cell
forest_fc$nb_count<- card(nb)

plot(forest_fc, 
     col = "white",
     border = "grey")
plot(nb, 
     coordinates(forest_fc), 
     add = T, 
     lwd = 2, 
     col = "black",
     pch = 16,
     cex = 0.5)
text(forest_fc, "nb_count", col = "red", cex = 1.2)

如何区分完全包围的多边形和开放边缘的多边形?

此解决方案结合了基于邻接和基于距离的邻域。相邻看台是在中央看台缓冲距离内的看台。如果满足以下条件,则支架有开放边缘:

  • 没有邻居
  • 邻居和周围林分之间的树高差异小于 5
  • 如果空间擦除‘buffer - neighbors’大于某个值,这里我使用 16 m。

这是一个考虑到开放边缘的不同情况的模式,但是它有相同数量的邻居:

我的函数逐行循环遍历 shapefile。对于每一行,它根据缓冲区识别一组邻居,并将站高与其邻居进行比较。如果差异小于 5,它会通过从缓冲区中删除邻居来额外检查是否存在间隙。

这是整个函数:

defineOpenEdge <- function(spdf, treeHeight, distance = 10, pixel.width = 16, ...) {

  # loop through the dataframe
  spdf@data$open_edge <- FALSE
  for (i in seq_along(spdf)) {

    # define stands and leftover forest
    one  = spdf[i, ]
    left = spdf[-i,]

    # Create buffer and intersectb buffer with neighbors: evalues if any are left?
    buff = buffer(one, distance)


    # Identify neighbors 
    nbrs.buff <- left[which(gOverlaps(sp::geometry(buff),
                                      sp::geometry(left), 
                                      byid = TRUE)),]

    # Conditions for open edge:
    #    - no neighbors
    if (nrow(nbrs.buff) == 0) {
      spdf@data[i,]$open_edge <- TRUE  

    } else {  # neighbors are smaller than the stands

      # Compare the height of the stands: 
      height.one  = rep(one@data$treeHeight, nrow(nbrs.buff))
      height.nbrs = nbrs.buff@data$treeHeight

      # Get the differences between the neighbouring stands
      difference = height.one - height.nbrs

      # compare here the tree heights of stands
      if(any(difference > 5)) {
        spdf@data[i,]$open_edge <- TRUE

      # Check if there is a big gap in neighborhood    
      } else {                     

        # Get the difference between two shapefiles???
        int.buff.one = rgeos::gDifference(buff, nbrs.buff + one)

        # Is the size of the openning larger than one pixel 16x16 m? 
        if (!is.null(int.buff.one) ) {

          # Calculate area of intersected data
          int.buff.one.area = gArea(int.buff.one)

          if (int.buff.one.area > 16*16) {
            spdf@data[i,]$open_edge <- TRUE
          }
        }
      }
    }
  }
 return(spdf) 
} 

这表明看台是否有开放边缘。在缓冲区大小为 10 m 时,我的开放边缘支架是: