Maybe somebody can help me with this:
I have a 4-dimensional spatiotemporal stars dataset, which contains annual values of a variable for four different tree species:
library(stars)
# 4-dimensional stars data: x,y,time, species
dat <- st_as_stars(array(data = runif(2000), dim = c(10, 10, 5, 4))) |>
setNames("data_val") |>
st_set_dimensions(names= c("x","y", "year", "tree_species")) |>
st_set_dimensions("year", values = 2018:2022) |>
st_set_dimensions("tree_species",values = c("bu", "fi", "ki", "ei"))
plot(dat) # (only values of the first slice of tree_speciess ("bu") displayed)
As a second object I have a species identity map, which contains information on which pixel belongs to which species:
# 2-d species map (x,y)
species_map <- st_as_stars(matrix(sample(c("bu", "fi", "ki", "ei"),size = 100, replace = TRUE),
ncol = 10, byrow=T)) |>
setNames("tree_species") |>
st_set_dimensions(c(1,2), names= c("x","y"))
species_map$tree_species <- factor(species_map$tree_species)
plot(species_map, col = c("#fdc086","#ffff99","#7fc97f","#beaed4"))
Based on this species_map, I want to extract pixel by pixel (x/y) the timeseries from the data that matches tree_species
. The resulting stars-object would be a 3-d array (as the 4th data dimension (tree_species) was collapsed), with the data-values in (x,y,year) coming from the respective species entry. So, in the upper-left corner of the resulting stars-array (species ei,ki,ei,bu) there would be the data-values from the 4th-dimension indexes (4,3,4,1).
All my attempts so far failed... I tried to use ifelse()
, which resulted in the right dimensionality, however it did not obtain the right results. I also tried to match values, but this also failed:
dat$data_val[, , , species_map$tree_species]
I guess my problem can be solved easily with some base R commands.
Thank you for your help.
All the best Paul
Based on the previous posts, I managed to solve this myself. Thank you for your help!
First we need to translate
tree_species
to the 4th dimension index indat
(like in Allan's for loop, see above), and then use JMenezes' indexmatrix, that just needed some little adjustments:Verification
It's diffcult to check wether everything works as expected with my initial example of random data. Therefore I create a second example of 'stars'-data with a fixed set of numbers varying along dimension 4. In the result, one pixel should finally hold the same value for each year. Also, I change from a square to rectangle map, to check if the rows and columns dimensions are alright.