[CHNOSZ-commits] r777 - in pkg/CHNOSZ: . R demo inst/tinytest
noreply at r-forge.r-project.org
noreply at r-forge.r-project.org
Fri Mar 10 15:57:40 CET 2023
Author: jedick
Date: 2023-03-10 15:57:39 +0100 (Fri, 10 Mar 2023)
New Revision: 777
Modified:
pkg/CHNOSZ/DESCRIPTION
pkg/CHNOSZ/R/thermo.R
pkg/CHNOSZ/demo/yttrium.R
pkg/CHNOSZ/inst/tinytest/test-thermo.R
Log:
Make argument handling in thermo() more like par()
Modified: pkg/CHNOSZ/DESCRIPTION
===================================================================
--- pkg/CHNOSZ/DESCRIPTION 2023-03-09 13:14:21 UTC (rev 776)
+++ pkg/CHNOSZ/DESCRIPTION 2023-03-10 14:57:39 UTC (rev 777)
@@ -1,6 +1,6 @@
-Date: 2023-03-09
+Date: 2023-03-10
Package: CHNOSZ
-Version: 1.9.9-68
+Version: 1.9.9-69
Title: Thermodynamic Calculations and Diagrams for Geochemistry
Authors at R: c(
person("Jeffrey", "Dick", , "j3ffdick at gmail.com", role = c("aut", "cre"),
Modified: pkg/CHNOSZ/R/thermo.R
===================================================================
--- pkg/CHNOSZ/R/thermo.R 2023-03-09 13:14:21 UTC (rev 776)
+++ pkg/CHNOSZ/R/thermo.R 2023-03-10 14:57:39 UTC (rev 777)
@@ -97,22 +97,65 @@
}
# A function to access or modify the thermo object 20190214
-thermo <- function(...) {
+# Revised for argument handling more like par() 20230310
+thermo <- function (...) {
+
+ # Get the arguments
args <- list(...)
- # Get the object
- thermo <- get("thermo", CHNOSZ)
+
+ # This part is taken from graphics::par()
+ # To handle only names in c(), e.g. thermo(c("basis", "species"))
+ if (all(unlist(lapply(args, is.character))))
+ args <- as.list(unlist(args))
+# # To handle an argument analogous to old.par in the example for ?par
+# # ... but it breaks the "Adding an element" example in ?thermo
+# if (length(args) == 1) {
+# if (is.list(args[[1L]]) || is.null(args[[1L]]))
+# args <- args[[1L]]
+# }
+
+ # Get the name of the arguments
+ argnames <- names(args)
+ # Use "" for the name of each unnamed argument
+ if(is.null(argnames)) argnames <- character(length(args))
+
+ # Get the current 'thermo' object
+ value <- original <- thermo <- get("thermo", CHNOSZ)
+ # Loop over arguments
if(length(args) > 0) {
- # Assign into the object
- slots <- names(args)
- for(i in 1:length(slots)) {
- # Parse the name of the slot
- names <- strsplit(slots[i], "$", fixed=TRUE)[[1]]
- if(length(names) == 1) thermo[[names]] <- args[[i]]
- if(length(names) == 2) thermo[[names[1]]][[names[2]]] <- args[[i]]
+
+ # Start with an empty return value with the right length
+ value <- vector("list", length(args))
+ for(i in 1:length(argnames)) {
+ if(argnames[i] == "") {
+ # For an unnnamed argument, retrieve the parameter from thermo
+ # Parse the argument value to get the slots
+ slots <- strsplit(args[[i]], "$", fixed = TRUE)[[1]]
+ names <- args[[i]]
+ } else {
+ # For a named argument, assign the parameter in thermo
+ # Parse the name of the argument to get the slots
+ slots <- strsplit(argnames[i], "$", fixed = TRUE)[[1]]
+ names <- argnames[i]
+ # Perform the assignment in the local 'thermo' object
+ if(length(slots) == 1) thermo[[slots[1]]] <- args[[i]]
+ if(length(slots) == 2) thermo[[slots[1]]][[slots[2]]] <- args[[i]]
+ }
+ # Get the (original) parameter value
+ if(length(slots) == 1) orig <- original[[slots[1]]]
+ if(length(slots) == 2) orig <- original[[slots[1]]][[slots[2]]]
+ # Put the parameter into the output value
+ if(!is.null(orig)) value[[i]] <- orig
+ names(value)[i] <- names
}
+ # Finally perform the assignment to 'thermo' in the CHNOSZ environment
assign("thermo", thermo, CHNOSZ)
- } else {
- # Return the object
- thermo
+
}
+
+ # Don't encapsulate a single unassigned parameter in a list
+ if(is.null(names(args)) & length(value) == 1) value <- value[[1]]
+ # Return the value
+ value
+
}
Modified: pkg/CHNOSZ/demo/yttrium.R
===================================================================
--- pkg/CHNOSZ/demo/yttrium.R 2023-03-09 13:14:21 UTC (rev 776)
+++ pkg/CHNOSZ/demo/yttrium.R 2023-03-10 14:57:39 UTC (rev 777)
@@ -128,7 +128,7 @@
# Use non-default ion size parameters 20230309
Bdot_acirc <- thermo()$Bdot_acirc
# Cl- and Y+3 override the defaults, and YCl+2 is a new species
-Bdot_acirc <- c("Cl-" = 4, "Y+3" = 5, "YCl+2" = 4, Bdot_acirc)
+Bdot_acirc <- c("Cl-" = 4, "Y+3" = 5, "YCl+2" = 4, "YCl2+" = 4, "YCl3" = 4, "YCl4-" = 4, Bdot_acirc)
thermo("Bdot_acirc" = Bdot_acirc)
# Run the functions to make plots for the demo
Modified: pkg/CHNOSZ/inst/tinytest/test-thermo.R
===================================================================
--- pkg/CHNOSZ/inst/tinytest/test-thermo.R 2023-03-09 13:14:21 UTC (rev 776)
+++ pkg/CHNOSZ/inst/tinytest/test-thermo.R 2023-03-10 14:57:39 UTC (rev 777)
@@ -16,3 +16,32 @@
# Also check propagation of NA for aqueous species
mod.OBIGT(name = "[Ala]", state = "aq", G = NA, S = NA)
expect_true(all(is.na(subcrt("[Ala]", "aq")$out[[1]]$G)), info = info)
+
+
+### Tests added 20230310 for changes to thermo() argument handling more like par()
+
+info <- "Alternative indexing styles give the same result"
+E1 <- thermo()$opt$E.units # The "old" way
+E2 <- thermo("opt$E.units") # The "new" way in CHNOSZ 2.0.0
+expect_equal(E2, E1, info = info)
+
+info <- "Value retrieved for opt$E.units is J"
+expect_equal(E1, "J", info = info)
+
+## Assign a strange value to opt$E.units
+#oldthermo <- thermo("opt$E.units" = 1234)
+#info <- "Restoring old parameter values is possible"
+#expect_silent(E3 <- thermo(oldthermo), info = info)
+#info <- "Old values are restored correctly"
+#E4 <- thermo("opt$E.units")
+#expect_equal(E4, E1, info = info)
+
+info <- "Parameters can be selected using c() or argument list"
+BS1 <- thermo("basis", "species")
+BS2 <- thermo(c("basis", "species"))
+expect_equal(BS1, BS2, info = info)
+
+info <- "Single parameter gives atomic vector"
+expect_null(names(E1), info = info)
+info <- "Two more parameters give named list"
+expect_equal(names(BS1), c("basis", "species"), info = info)
More information about the CHNOSZ-commits
mailing list