I'm attempting to use the sf package and a piped/tidyverse workflow to generate bounding boxes based on groups defined in another column. I think it should work like below, but it seems like st_bbox is not respecting groups.
I expect to receive three polygon records that represent bounding boxes around proints from a, b, and c, but instead I receive three polygon records that represent bounding boxes for all points.
library(dplyr)
library(sf)
a <- data.frame(group=rep('a',100), lon=rnorm(100,11,.2), lat=rnorm(100,53,.2))
b <- data.frame(group=rep('b',100), lon=rnorm(100,11.5,.2), lat=rnorm(100,53.5,.2))
c <- data.frame(group=rep('c',100), lon=rnorm(100,12,.2), lat=rnorm(100,54,.2))
dat <- rbind(a,b,c)
pts <- dat %>% st_as_sf(coords=c('lon','lat'),crs=4326)
pts %>%
group_by(group) %>%
summarize(geometry = st_as_sfc(st_bbox(geometry)))
This returns:
Simple feature collection with 3 features and 1 field
geometry type: POLYGON
dimension: XY
bbox: xmin: 10.34313 ymin: 52.43993 xmax: 12.54254 ymax: 54.54012
epsg (SRID): 4326
proj4string: +proj=longlat +datum=WGS84 +no_defs
# A tibble: 3 x 2
group geometry
<fct> <POLYGON [°]>
1 a ((10.34313 52.43993, 12.54254 52.43993, 12.54254 54.54012, 10.34313 54.54012, 10.34313 52...
2 b ((10.34313 52.43993, 12.54254 52.43993, 12.54254 54.54012, 10.34313 54.54012, 10.34313 52...
3 c ((10.34313 52.43993, 12.54254 52.43993, 12.54254 54.54012, 10.34313 54.54012, 10.34313 52...
One option is to use a nested dataframe using tidyr::nest
and then purrr::map
. I also used a wrapper function to simplify the map
call
library(tidyverse)
box_sf <- pts %>%
group_by(group) %>%
nest()
bbox_wrap <- function(x) st_as_sfc(st_bbox(x))
box_sf <- box_sf %>%
mutate(bbox = map(data, bbox_wrap))
This will give you a list of bounding boxes as a column of a dataframe. If you want to convert back to an sf
object you can do this:
box_sf %>%
mutate(geometry = st_as_sfc(do.call(rbind, bbox))) %>%
select(-data, -bbox) %>%
st_as_sf()
Seems a little roundabout, I'm hoping to see a solution using group_by
as you originally intended
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With