user1988
user1988

Reputation: 29

How to calculate the distance of raster to the nearest polygon?

I have an empty raster file (r1, Rasterlayer) and I want to calculate for each of the non-NA cells, the euclidian distance to the nearest polygons (S1, SpatialPolygonsDataFrame). Both r1 and S1 are projected in utm. Is there any R package that can do that?

Upvotes: 0

Views: 2251

Answers (3)

Sam
Sam

Reputation: 1482

this is something i would like to find in a one off function also - similar to raster::distance but telling you which polygon each cell is closest to, via an ID field or some such.

Annyhoo, for now;

# make a dummy raster with some dummy data. 
r <- raster(xmn = 50, xmx = 80, ymn = -7, ymx = 10, res=0.5)
r[] <- sample(1:10,ncell(r), replace=T)

# make some dummy polygons that you want to know the min distance to on your raster
p1 <- rbind(c(55,-5), c(65,-5), c(65, 0), c(55,0), c(55,-5))
p2 <- rbind(c(70,-5), c(75,-5), c(75, 2), c(70,2), c(70,-5))
p3 <- rbind(c(55,4), c(75,4), c(75, 7), c(55,7), c(55,4))
pols <- st_as_sf(spPolygons(p1,p2,p3))
pols$ID <- 1:3

# let's look
plot(r)
plot(pols$geometry,add=T)

enter image description here

# to make a raster layer of min euclidean distance to a polygon (any),
# loop through the sf ID's and `fasterize` (v. quick) and run the 
# raster::distance function to find out the distance from itself

st <- stack()

for(i in pols$ID){
  r_pol <- fasterize(pols[pols$ID==i,], r, field="ID")
  rd <- distance(r_pol)
  st <- stack(st,rd)
}

# To produce a simple min distance from any polygon, just select the min from the stack
r_min_dis_any_pol <- min(st)
plot(r_min_dis_any_pol)

enter image description here

# to go a bit further and let you know to which polygon the min distance refers to
r_min_which_pol <- which.min(st)
plot(r_min_which_pol)

enter image description here

# if you were interested in a zonal sum of the raster data, dependent on its nearest polygon

zonal_sum <- zonal(r, r_min_which_pol, fun="sum")

identical(sum(zonal_sum[,2]), cellStats(r,sum))
[1] TRUE

Upvotes: 0

Robert Hijmans
Robert Hijmans

Reputation: 47071

You can first rasterize, and then use distance.

library(raster)
p1 <- rbind(c(-180,-20), c(-140,55), c(10, 0), c(-140,-60), c(-180,-20))
pols <- spPolygons(p1)
r <- raster(ncol=90, nrow=45)
r <- rasterize(pols, r)

d <- distance(r)

(The strange looking pattern is because the raster has lon/lat coordinates that wrap around the date line)

Upvotes: 1

AlSub
AlSub

Reputation: 1155

You can use distance function from library(raster), this function returns the distance, for all cells that are NA, to the nearest cell that is not NA:

install.packages('raster')
library(raster)

distance(r1, S1, filename = 'raster_distance', doEdge= TRUE)

Upvotes: 0

Related Questions