rmapsrasterareaspatial-data-frame

Calculating area from Large spatialPixelsDataFrame


I have an object called cr1 which is a large SpatialPixelsDataFrame of a lake. Here is a link to the file: https://www.dropbox.com/s/uuvlmxmri144hp2/macrosmall.rdata?dl=0

I think each pixel has has a 1m x 1m cell size, however i think this attribute is nowhere specified. "macro" is the measured height of submersed macrophytes in the lake. The structure looks like this.

    Formal class 'SpatialPixelsDataFrame' [package "sp"] with 7 slots

  ..@ data       :'data.frame': 252234 obs. of  1 variable:
  .. ..$ macro: num [1:252234] 0.0468 0.0518 0.0445 0.046 0.0477 ...

  ..@ coords.nrs : num(0) 

  ..@ grid       :Formal class 'GridTopology' [package "sp"] with 3 slots

  .. .. ..@ cellcentre.offset: Named num [1:2] 3404494 5872334

  .. .. .. ..- attr(*, "names")= chr [1:2] "x" "y"
  .. .. ..@ cellsize         : Named num [1:2] 1 1

  .. .. .. ..- attr(*, "names")= chr [1:2] "x" "y"
  .. .. ..@ cells.dim        : Named int [1:2] 776 536

  .. .. .. ..- attr(*, "names")= chr [1:2] "x" "y"
  ..@ grid.index : int [1:252234] 415333 415334 415335 415336 415337 415338 
415339 414554 414555 414556 ...

  ..@ coords     : num [1:252234, 1:2] 3404666 3404667 3404668 3404669 3404670 ...
  .. ..- attr(*, "dimnames")=List of 2

  .. .. ..$ : chr [1:252234] "949" "950" "951" "952" ...

  .. .. ..$ : chr [1:2] "x" "y"

  ..@ bbox       : num [1:2, 1:2] 3404493 5872333 3405269 5872869

  .. ..- attr(*, "dimnames")=List of 2

  .. .. ..$ : chr [1:2] "x" "y"

  .. .. ..$ : chr [1:2] "min" "max"

  ..@ proj4string:Formal class 'CRS' [package "sp"] with 1 slot

  .. .. ..@ projargs: chr NA

I would like to calculate the area that is covered for certain macrophyte height intervals (i.e. the area covered for intervals of "macro").

How can I specify the resolution or size of each cell (=1m x 1m)? Which package and function handles the area estimation of the SpatialPixelsDataFrame?

I actually only loaded the map so far

library(sp)
library(raster)

load("macrosmall.rdata")

and tried a couple of things:

area(cr1)

This would be an example of what I want and how I want to calculate it, however the specifications of the dataframe don't allow it

intervals <- list(c(0.1,0.2), 
              c(0.2,0.3),
              c(0.3,0.4))

sapply(intervals, function(x) { 
  sum(cr1[] > x[1] & cr1s[] <= x[2])
})

But I basically always end up with the same warning messages

Warning message: In .local(x, ...) : This function is only useful for Raster* objects with a longitude/latitude coordinates

Please note that the area in question is quite small (25 ha).

Can anyone push me into the right direction?


Solution

  • I am really confused. You said you are working on a spatialPixelsDataFrame, but the data you provided, cr1, is a raster object.

    Anyway, here I showed a possible solution to calculate the area.

    library(sp)
    library(raster)
    
    # Load the RData
    load("macrosmall.RData")
    
    # View the raster layer
    cr1
    # class       : RasterLayer 
    # dimensions  : 200, 269, 53800  (nrow, ncol, ncell)
    # resolution  : 1, 1  (x, y)
    # extent      : 3405000, 3405269, 5872500, 5872700  (xmin, xmax, ymin, ymax)
    # coord. ref. : NA 
    # data source : in memory
    # names       : macro 
    # values      : 0, 1.896009  (min, max)
    
    # Plot the raster layer
    plot(cr1)
    

    enter image description here

    I am not sure what raster values indicate the "lake". Assuming that all the non-NA cells are the lake, we can then do the following.

    # Get all cell values
    cells <- values(cr1)
    
    # Remove NA
    cells_nonNA <- cells[!is.na(cells)]
    
    # Count how many cells
    length(cells_nonNA)
    # [1] 36143
    

    Since 1 cell is one 1 m^2, the total lake area is 36143 m^2.

    Assuming that the raster values for the lake are above 1, we can again subset the cell values.

    cells_above1 <- cells_nonNA[cells_nonNA > 1]
    length(cells_above1)
    # [1] 77