在R中裁剪简单要素对象


20

是否有用于裁剪sf映射对象的函数,类似于maptools::pruneMap(lines, xlim= c(4, 10), ylim= c(10, 15))用于SpatialPolygon或SpatialLine的函数?

我正在考虑,st_intersection()但是可以有适当的方法。

Answers:


17

st_intersection可能是最好的方法。寻找使sf对象与您的输入相交的最佳方法。这raster::extent是兼顾新旧便利的一种方式。nc由创建example(st_read)

st_intersection(nc, st_set_crs(st_as_sf(as(raster::extent(-82, -80, 35, 36), "SpatialPolygons")), st_crs(nc)))

我不认为您可以哄骗st_intersection不需要完全匹配的CRS,因此要么将它们都设置为NA,要么确保它们相同。没有用于bbox / extent afaik的简便工具,因此使用栅格是使事情变得简单的好方法。


非常感谢@mdsumner,它像一种魅力。我花了几个小时,st_intersection但自己解决不了。
Kazuhito

现在,您可以spex::spex用来替换st_as_sf(as(...))呼叫。另外,tmaptools::crop_shape()可以做到这一点。
AF7

1
sf现在包括st_crop,有关详细信息,请参见我的答案。
AF7

22

从今天开始,(st_crop的github版本中就有一个函数,不久的将来也可能在CRAN上)。sfdevtools::install_github("r-spatial/sf")

只是发出:

st_crop(nc, c(xmin=-82, xmax=-80, ymin=35, ymax=36))

矢量必须xmin xmax ymin ymax(以任何顺序)命名。

您还可以使用任何可以被st_bbox裁剪限制读取的对象,这非常方便。


5

另一个解决方法,对我来说,较大的shapefile更快:

library(sf)
library(raster)
library(rgeos)
library(ggplot2)

# Load National Forest shapefile
# https://data.fs.usda.gov/geodata/edw/edw_resources/shp/S_USA.AdministrativeForest.zip
nf.poly <- st_read("S_USA.AdministrativeForest"), "S_USA.AdministrativeForest")

crop_custom <- function(poly.sf) {
  poly.sp <- as(poly.sf, "Spatial")
  poly.sp.crop <- crop(poly.sp, extent(c(-82, -80, 35, 36)))
  st_as_sf(poly.sp.crop)
}

cropped <- crop_custom(nf.poly)

谢谢。这是有趣的工作流程,是我的raster :: crop()和st_as_sf()... + 1的组合。我希望我们在sf的未来版本中可以拥有这类易于访问的函数,例如crop()。至于速度,在您的数据集上以您的函数报告的用户:5.42,系统:0.09,经过5.52快速运行system.time ,而st_intersection()方法用户:1.18,系统:0.05,经过了1.23。(可能我的环境与您的环境有所不同...不确定。)
Kazuhito

这很有趣-st_intersection方法对我来说大约需要80秒钟。
pbaylis'4-4-3

请记住,将raster :: crop函数应用于sp几何对象时,它充当rgeos函数的包装器。虽然,这是一个非常方便的包装器。GEOS API在WKT对象上运行,因此,它将始终是sf覆盖操作的标准。
杰弗里·埃文斯

1
而且它会随着时间而变化,sf现在在0.5-1 cran.r-project.org/web/packages/sf/news.html中内置了“空间索引”, 因此现在可能比sp / rgeos更快。
mdsumner'7

1
sf现在包括st_crop,有关详细信息,请参见我的答案。
AF7

1

@mdsumner的解决方案作为函数。适用rasta于RasterBrick,范围,bbox等。

# Crop a Simple Features Data Frame to the extent of a raster
crop.sf = function(sfdf, rasta) {
  st_intersection(sfdf, st_set_crs(st_as_sf(as(extent(rasta), "SpatialPolygons")), st_crs(sfdf)))
}

它丢弃了栅格的crs信息,因为我不知道如何将栅格crs()转换为st_crs()

在我的机器上以及对于我的数据样本,这具有raster::crop与SpatialLinesDataFrame版本的数据等效的性能。

@pbaylis的解决方案慢了大约2.5倍:

# Slower option.
crop.sf2 = function(sfdf, rasta) {
  st_as_sf(crop(as(sfdf, "Spatial"), rasta))
}

编辑:某人评论建议spex,如果有crs,它将从rasta产生crs生成SpatialPolygons。

此代码使用与spex相同的方法:

# Crop a Simple Features Data Frame to the extent of a raster
crop.sf3 <- function(sfdf, rasta) {
  # Get extent and crs
  ext.sp <- as(extent(rasta), "SpatialPolygons")
  crs(ext.sp) <- crs(rasta)

  # crop
  st_intersection(sfdf, st_as_sf(ext.sp))
}

sf现在具有st_crop可能值得检查的功能。
cmc
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.