Skip to contents

The dimension Spat and Time based on the package terra and lubridate, so it’s necessary to load this package:

library(terra)
#> Warning: package 'terra' was built under R version 4.1.3
#> terra 1.5.21
library(lubridate)
#> Warning: package 'lubridate' was built under R version 4.1.2
#> 
#> Attaching package: 'lubridate'
#> The following objects are masked from 'package:terra':
#> 
#>     intersect, union
#> The following objects are masked from 'package:base':
#> 
#>     date, intersect, setdiff, union

Create the TSD-data

TimeRastData based on Raster data

There are two ways to create the TimeRastData, either read Raster-Cluster (multi-layers) into array or terra::SpatRaster:

Load data

In this tutorial will convert three days meteorological data (potential ET) from ReKIS to TSD-data, the original data is saved as one of the raster format ASC-format.

## get the file path and names of raster data (in .asc)
fp_Extdata <- system.file("extdata", package = "TimeSpatData") 
fn_Asc <-  list.files(fp_Extdata, ".asc")

## read data into SpatRaster and array
rast_ET <- rast(file.path(fp_Extdata, fn_Asc[1:3]))  # the first six lines are the metadata
ary_ET <- as.array(rast_ET)

## check the data:
rast_ET 
#> class       : SpatRaster 
#> dimensions  : 190, 240, 3  (nrow, ncol, nlyr)
#> resolution  : 1000, 1000  (x, y)
#> extent      : 4480000, 4720000, 5550000, 5740000  (xmin, xmax, ymin, ymax)
#> coord. ref. :  
#> sources     : ET_1961-01-01.asc  
#>               ET_1961-01-02.asc  
#>               ET_1961-01-03.asc  
#> names       : ET_1961-01-01, ET_1961-01-02, ET_1961-01-03
str(ary_ET)
#>  num [1:190, 1:240, 1:3] 0.5 0.5 0.5 0.5 0.5 0.5 0.5 0.5 0.5 0.5 ...

From array to TimeRastData

The convention of TSD-Data define the fest order of dimensions, therefor the dimension of array must be consistent like aim TSD-Data stay.

The TSD-data anfordert always the geological information (Spat), but the array data class can’t save any geological data, so we need still set the arguments Spat_EPSG and Spat_extent:

The dimension Time just need to convert the timestempal to the Date with lubridate

NOTE: The TSD-Data define the y-Aches always from SMALL to BIG, but the most raster data save them from north to south, so the y-value ist from big to small. Therefor we need adjust this dimension.

## reform the array
ary_ET_reformed <- ary_ET[190:1,,] |> aperm(c(3,2,1))

## get the geological info
ext_Template <- ext(rast_ET)

## convert to TSD
tsd_ET_a <- new_TimeRastVariable(ary_ET_reformed, # data
                               "ET", "mm/d", # name and unit
                               as_date(c("1961-01-01", "1961-01-02", "1961-01-03")), # time
                               31468, ext_Template) # Spat
#> The reselutions are:
#> x: 1000
#> y: 1000
#> They will not be checked, please make sure they are correct.

## check
str(tsd_ET_a)
#>  'TimeRastVariable' num [1:3, 1:240, 1:190] 0.3 0.3 0.3 0.3 0.3 ...
#>  - attr(*, "dimnames")=List of 3
#>   ..$ : chr [1:3] "1961-01-01" "1961-01-02" "1961-01-03"
#>   ..$ : NULL
#>   ..$ : NULL
#>  - attr(*, "Name")= chr "ET"
#>  - attr(*, "Unit")= Units: [mm/d] num 1
#>  - attr(*, "Time")= Date[1:3], format: "1961-01-01" "1961-01-02" ...
#>  - attr(*, "Spat_crs")= num 31468
#>  - attr(*, "Spat_extent")=Formal class 'SpatExtent' [package "terra"] with 1 slot
#>   .. ..@ ptr:Reference class 'Rcpp_SpatExtent' [package "terra"] with 2 fields
#>   .. .. ..$ valid : logi TRUE
#>   .. .. ..$ vector: num [1:4] 4480000 4720000 5550000 5740000
#>   .. .. ..and 28 methods, of which 14 are  possibly relevant:
#>   .. .. ..  align, as.points, ceil, compare, deepcopy, finalize, floor,
#>   .. .. ..  initialize, intersect, round, sample, sampleRandom, sampleRegular,
#>   .. .. ..  union

This method is first recognized, because it can easy deal with the huge data.

From SpatRaster to TimeRastData

The second method is only recognized for data that contain not so many time step in Time dimension.

## add the crs infomation to the data, this depend on wether the raster-file contain this infomation, 
## when es contauin this info in original, then this step is not necessery
crs(rast_ET) <- "EPSG:31468"
## convert to TSD
tsd_ET_r <- new_TimeRastVariable(rast_ET, # data
                               "ET", "mm/d", # name and unit
                               as_date(c("1961-01-01", "1961-01-02", "1961-01-03"))) # time

## check
str(tsd_ET_r)
#>  'TimeRastVariable' num [1:3, 1:240, 1:190] 0.3 0.3 0.3 0.3 0.3 ...
#>  - attr(*, "dimnames")=List of 3
#>   ..$ : chr [1:3] "1961-01-01" "1961-01-02" "1961-01-03"
#>   ..$ : NULL
#>   ..$ : NULL
#>  - attr(*, "Name")= chr "ET"
#>  - attr(*, "Unit")= Units: [mm/d] num 1
#>  - attr(*, "Time")= Date[1:3], format: "1961-01-01" "1961-01-02" ...
#>  - attr(*, "Spat_crs")= chr "31468"
#>  - attr(*, "Spat_extent")=Formal class 'SpatExtent' [package "terra"] with 1 slot
#>   .. ..@ ptr:Reference class 'Rcpp_SpatExtent' [package "terra"] with 2 fields
#>   .. .. ..$ valid : logi TRUE
#>   .. .. ..$ vector: num [1:4] 4480000 4720000 5550000 5740000
#>   .. .. ..and 28 methods, of which 14 are  possibly relevant:
#>   .. .. ..  align, as.points, ceil, compare, deepcopy, finalize, floor,
#>   .. .. ..  initialize, intersect, round, sample, sampleRandom, sampleRegular,
#>   .. .. ..  union

TimeVectData based on Vector (and table) data

Compare to the raster data, the vector data save always only the geometric data, the other time-based data will be saved in separated data. Therefor the both parties are always needed by the create of the TimeVectData.

Load data

The polygons of Catchments “Mulde” and “Speree” in Saxony, German is download from iDA (interdisziplinäre Daten und Auswertungen) and in GPKG-Format reformed.

## load polygon
polygon_SAX <- vect(file.path(fp_Extdata, "shp_SAX_EZG.gpkg"))

## random array data
ary_Q <- array(runif(10, 0, 6), c(5, 2)) # random number for two `Spat` (polygons) and five `Time` (time steps)

From SpatVector and array to TimeVectData

NOTE: the Spat_Data MUST contain the attribute “Spat_ID”

## convert to TSD
tsd_Q_v <- new_TimeVectVariable(ary_Q, # data
                               "Q", "m3/s", # name and unit
                               as_date(c("1961-01-01", "1961-01-02", "1961-01-03", "1961-01-04", "1961-01-05")), # time
                               c("PID560051", "PID582820"), # Spat_ID
                               polygon_SAX) # Spat data, that must contain the attribute "Spat_ID"

## check
str(tsd_Q_v)
#>  'TimeVectVariable' num [1:5, 1:2] 5.41 3.45 3.23 1.03 3.63 ...
#>  - attr(*, "dimnames")=List of 2
#>   ..$ : chr [1:5] "1961-01-01" "1961-01-02" "1961-01-03" "1961-01-04" ...
#>   ..$ : chr [1:2] "PID560051" "PID582820"
#>  - attr(*, "Name")= chr "Q"
#>  - attr(*, "Unit")= Units: [m3/s] num 1
#>  - attr(*, "Time")= Date[1:5], format: "1961-01-01" "1961-01-02" ...
#>  - attr(*, "Spat_ID")= chr [1:2] "PID560051" "PID582820"
#>  - attr(*, "Spat_Data")=Formal class 'PackedSpatVector' [package "terra"] with 5 slots
#>   .. ..@ type       : chr "polygons"
#>   .. ..@ crs        : chr "PROJCRS[\"ETRS89 / UTM zone 33N\",\n    BASEGEOGCRS[\"ETRS89\",\n        DATUM[\"European Terrestrial Reference"| __truncated__
#>   .. ..@ coordinates: num [1:16478, 1:2] 368467 368393 368290 368206 368109 ...
#>   .. .. ..- attr(*, "dimnames")=List of 2
#>   .. .. .. ..$ : NULL
#>   .. .. .. ..$ : chr [1:2] "x" "y"
#>   .. ..@ index      : num [1:2, 1:4] 1 2 1 1 0 ...
#>   .. .. ..- attr(*, "dimnames")=List of 2
#>   .. .. .. ..$ : NULL
#>   .. .. .. ..$ : chr [1:4] "geom" "part" "hole" "start"
#>   .. ..@ attributes :'data.frame':   2 obs. of  1 variable:
#>   .. .. ..$ Spat_ID: chr [1:2] "PID560051" "PID582820"