...
 
Commits (2)
......@@ -50,9 +50,53 @@ read_vars_to_cube <- function(vardefs, attrs_to_read=as.character(c()), offset=N
attr(cube, 'extent') <- extent
attr(cube, 'ids') <- ids
for (attr in attrs_to_read) {
attr(cube, attr) <- vars[[1]]$attrs[[attr]]
for (att in lapply(attrs_to_read, parse_attr)) {
attr(cube, att$key) <- find_attr(vars[[1]], att)
}
return(cube)
}
find_attr <- function(data, att) {
if (is.null(att$var)) {
# No source variable specified.
# First, try to read a global attribute.
val <- data$attrs[[att$key]]
if (!is.null(val)) {
return(val)
}
# Didn't find it as a global attribute.
# Start looking through the regular variables.
for (var in names(data$data)) {
val <- attr(data$data[[var]], att$key)
if (!is.null(val)) {
return(val)
}
}
# Try checking no-data variables
for (a in data$attrs) {
if (is.list(a)) {
val <- a[[att$key]]
if (!is.null(val)) {
return(val)
}
}
}
return(NULL)
} else {
# Is the variable a regular variable?
if (att$var %in% names(data$data)) {
return(attr(data$data[[att$var]], att$key))
}
# Is it a no-data variable?
if (att$var %in% names(data$attrs) && is.list(data$attrs[[att$var]])) {
return(data$attrs[[att$var]][[att$key]])
}
return(NULL)
}
}
......@@ -299,9 +299,18 @@ test_that("we can read multiple spatial variables into a cube", {
extent <- c(20, 80, 30, 70)
write_vars_to_cdf(data, fname, extent=extent)
cube <- read_vars_to_cube(fname)
write_vars_to_cdf(data, fname, extent=extent, attrs=list(
list(var=NULL, key='globalatt', val=12345),
list(var='location', key='units', val='kilocalories'),
list(var='location', key='units_abbrev', val='kcal')
))
cube <- read_vars_to_cube(fname,
attrs_to_read=c('globalatt', # global attribute specified as such
'location:units', # attribute of named regular variable
'units_abbrev', # attribute of unnamed regular variable
'crs:grid_mapping_name', # attribute of named no-data variable
'location:doesnotexist')) # non-existant attribute
expect_equal(attr(cube, "extent"), extent)
expect_equal(cube[,,"location"], data$location)
......@@ -310,6 +319,13 @@ test_that("we can read multiple spatial variables into a cube", {
expect_equal(dimnames(cube)[[3]], c('location', 'scale', 'shape'))
expect_equal(attr(cube, 'globalatt'), 12345)
expect_equal(attr(cube, 'units'), 'kilocalories')
expect_equal(attr(cube, 'units_abbrev'), 'kcal')
expect_equal(attr(cube, 'grid_mapping_name'), 'latitude_longitude')
expect_null(attr(cube, 'doesnotexist'))
file.remove(fname)
})
......
#!/usr/bin/env Rscript
# Copyright (c) 2018 ISciences, LLC.
# Copyright (c) 2018-2019 ISciences, LLC.
# All rights reserved.
#
# WSIM is licensed under the Apache License, Version 2.0 (the "License").
......@@ -43,7 +43,7 @@ main <- function(raw_args) {
expanded_inputs <- wsim.io::expand_inputs(args$input)
wsim.io::info('Preparing to load vars from', length(expanded_inputs), "files.")
inputs_stacked <- wsim.io::read_vars_to_cube(expanded_inputs)
inputs_stacked <- wsim.io::read_vars_to_cube(expanded_inputs, attrs_to_read=c('units', 'standard_name'))
if (length(unique(dimnames(inputs_stacked)[[3]])) > 1) {
wsim.io::die_with_message("Can't perform fit on heterogeneous input variables ( received input variables:",
......@@ -68,11 +68,14 @@ main <- function(raw_args) {
extent=attr(inputs_stacked, 'extent'),
ids=attr(inputs_stacked, 'ids'),
attrs=c(
output_attrs,
list(
list(var=NULL,key="distribution",val=distribution),
list(var=NULL,key="variable",val=fit_param_name)
)))
list(var=NULL,key="variable",val=fit_param_name),
list(var=NULL,key="units", val=attr(inputs_stacked, "units")),
list(var=NULL,key="standard_name", val=attr(inputs_stacked, "standard_name"))
),
output_attrs # include output_attrs after standard attrs so that we can overwrite defaults (e.g., unit change)
))
wsim.io::info('Wrote fits to', outfile)
}
......