I would like to take a spatial layer with overlapping polygons and transform it so that a layer without any overlaps is created, and the attributes of the overlapping polygons aggregated as a list, or a sum (will vary depending on the field and goal of analysis). Based on these posts https://github.com/r-spatial/sf/issues/1230 , summarise attributes from sf::st_intersection() where geometries overlaps I think that I should be able to do this using the origins field created when st_intersection() is used with a single input.
An example with some dummy data:
set.seed(123)
p1 = st_cast(st_sfc(st_multipoint(cbind(runif(10),runif(10)))),"POINT")
b1 =st_buffer(p1, .15)
b1d = data.frame(id=1:10, class=rep(c("high", "low"), times=5), value= rep(c(10,5),times=5))
b1d$geometry = b1
b1d = st_as_sf(b1d)
b1d_intersect <- st_intersection(b1d)%>%
mutate(id_int=seq(from=1, to=nrow(.), by=1)) %>%
st_collection_extract()
ggplot(b1d)+geom_sf(aes(fill=class), alpha=0.5)
ggplot(b1d_intersect)+geom_sf(aes(fill=class), alpha=0.5)
In my desired output the attributes of each polygon would aggerate overlapping attribute values, something like:
b1d_intersect_values <- b1d_intersect %>%
group_by(rownames(.)) %>%
summarise(Class_List=paste0(class, collapse = "; "), value_sum=sum(value))
but that actually works by linking back to the original b1d layer using the origins field? I feel like I need to use map() somewhere in there.
I've also tried to tackle it using st_join, but that doesn't work quite right as it is assigning multiple classes for polygons where n.overlaps=1, and it also seems as though would take longer than using an index when applied to large data sets as it would require the additional spatial processing step with st_join.
b1d_intersect_values_2 <- st_join(b1d_intersect, b1d) %>%
group_by(id_int, n.overlaps) %>%
summarise(class_list=paste0((class.y),collapse="; "), value_sum=sum(value.y))
Any suggestions on how to proceed would be appreciated.
Figured it out eventually, answering myself so nobody wastes time or effort, and in case helpful to anyone else.
b1d_intersect_values <- b1d_intersect %>%
mutate(class_list=map_chr(origins, ~ paste0(class[.], collapse = "; ")),
value_sum=map_dbl(origins, ~ sum(value[.])))
ggplot(b1d_intersect_values)+geom_sf(aes(fill=class_list, alpha=value_sum))