Search code examples
rlapplyrasterpurrr

Use an arrow assignment function as R purrr map2


I have a list of rasters:

filelist <- as.list(c("rasterA", "rasterB") # name them
rasterlist <- lapply(filelist, function(x) raster::raster(x)) # read them in

And a list of CRSes corresponding to those rasters:

crslist <- as.list(c("crsA.Rds", "crsB.Rds")) # name them
crslist %<>% lapply(function(x) readRDS(x)) # read them in

To fill the @crs slot in a raster you use (e.g.):

raster::crs(rasterA) <- crsA

But I can't work out how to use this arrow assignment in a purrr::map2 call. The example in the R cheat sheet is map2(x, y, sum), but sum works on vectors, is directionless, and contains all of its terms within its brackets.

Reading the map2 help, I tried the formula format:

purrr::map2(rasterlist, crslist, ~ raster::crs(.x) <- .y)

But no dice:

Error in as_mapper(.f, ...) : object '.y' not found

Does anyone know how I'd do this? Currently I'm using a loop which is simple, but I'm trying to force myself to learn mapping and keep hitting these kinds of walls.

for (i in length(rasterlist)) {
 crs(rasterlist[[i]]) <- crslist[[i]]
}

Thanks!

Starting condition:

NA crs

After for loop:

forloop

After raster_assigner function instead:

rasterassigner

Hopefully this is salvagable because I've got other use cases like this. Cheers!


Solution

  • We may need

    purrr::map2(rasterlist, crslist, ~ {crs(.x) <- .y;.x})
    

    It is not related to the raster - as the simple example below shows the same error

    > map2(list(1, 2, 3), list(3, 4, 5), ~ names(.x) <- .y)
    Error in as_mapper(.f, ...) : object '.y' not found
    > map2(list(1, 2, 3), list(3, 4, 5), ~ {names(.x) <- .y; .x})
    [[1]]
    3 
    1 
    
    [[2]]
    4 
    2 
    
    [[3]]
    5 
    3 
    

    However this won't return an error in Map (but it is not correct because the output returned is without the names, unless we wrap it with {} and return the x

    > Map(function(x, y) names(x) <- y, list(1, 2, 3), list(3, 4, 5))
    [[1]]
    [1] 3
    
    [[2]]
    [1] 4
    
    [[3]]
    [1] 5