| Title: | Trade and Environment Equilibrium Modeling System |
| Version: | 1.0.0 |
| Description: | Equilibrium models are frequently employed to examine the potential impacts of economic, energy, and trade policies as well as form the foundation of most integrated assessment models. The 'teems' package handles all aspects of running equilibrium models while facilitating transparent and reproducible workflows. |
| License: | AGPL (≥ 3) |
| URL: | https://teemsphere.github.io/, https://github.com/teemsphere/teems/ |
| BugReports: | https://github.com/teemsphere/teems/issues |
| Depends: | R (≥ 4.3.0) |
| Imports: | cli (≥ 3.4.0), data.table (≥ 1.15.0), graphics, grDevices, jsonlite (≥ 1.8.0), purrr (≥ 1.0.0), R6 (≥ 2.4.0), rlang (≥ 1.0.0), stats, tibble (≥ 3.0.0), tools, utils |
| Suggests: | testthat (≥ 3.0.0), withr (≥ 3.0.0) |
| LinkingTo: | cpp11 |
| Config/testthat/edition: | 3 |
| Encoding: | UTF-8 |
| Language: | en-US |
| RoxygenNote: | 7.3.3 |
| SystemRequirements: | Docker (https://www.docker.com) |
| NeedsCompilation: | yes |
| Packaged: | 2026-10-17 20:02:49 UTC; mpc |
| Author: | Matthew Cantele |
| Maintainer: | Matthew Cantele <matthew.cantele@protonmail.com> |
| Repository: | CRAN |
| Date/Publication: | 2026-10-17 20:30:02 UTC |
Load GTAP HAR files and convert data formats
Description
GTAP_convert() reads a GTAP database's HAR
files into lists of arrays at full resolution. With target
it can also convert a standard GTAP database between the
classic v6.2 and standard v7 data formats, or prepare a
GTAP-AEZ, GTAP-E or GTAP-Power database for the respective
model. The output can be inspected or modified in R, passed
directly to ems_data() via its dat_input, par_input,
and set_input arguments, or written to disk for later use.
Usage
GTAP_convert(dat_har, par_har, set_har, target = NULL)
Arguments
dat_har |
Character vector of length 1, file name in working directory or path to a GTAP HAR file with basedata coefficient data. |
par_har |
Character vector of length 1, file name in working directory or path to a GTAP HAR file with parameter coefficient data. |
set_har |
Character vector of length 1, file name in working directory or path to a GTAP HAR file with set elements and attributes. |
target |
Character vector of length 1 (default is
|
Value
A named list with elements dat, par, and set,
each containing a list of arrays corresponding to database
headers. Suitable for direct use with ems_data().
See Also
ems_data() for loading and preparing converted
data for a model run.
Examples
## Not run:
# The following examples require input data. See
# https://teemsphere.github.io/ to get started.
# Convert HAR files to lists of arrays
ls_arrays <- GTAP_convert(
dat_har = "path/to/gsdfdat.har",
par_har = "path/to/gsdfpar.har",
set_har = "path/to/gsdfset.har"
)
# Convert v7.0 files to v6.2 format
converted2v6 <- GTAP_convert(
dat_har = "v7_data/gsdfdat.har",
par_har = "v7_data/gsdfpar.har",
set_har = "v7_data/gsdfset.har",
target = "GTAPv6"
)
# Convert v6.2 files to v7.0 format
converted2v7 <- GTAP_convert(
dat_har = "v6_data/gsddat.har",
par_har = "v6_data/gsdpar.har",
set_har = "v6_data/gsdset.har",
target = "GTAPv7"
)
## End(Not run)
Solve a model with a Runge-Kutta method
Description
An ems_solve() wrapper restricted to the
Runge-Kutta methods, with the step controls that exist only
for them and defaults chosen for them: adaptive "DoPri54"
from four initial steps.
Usage
ems_RK(
cmf_path,
solution_method = c("DoPri54", "BoSha32", "RK4", "Heun", "RK2"),
steps = 4L,
eps_tolerance = 0.01,
adaptive = NULL,
matrix_method = c("LU", "DBBD", "SBBD", "NDBBD"),
n_tasks = 1L,
n_threads = 1L,
precision = c("single", "double"),
n_subintervals = 1L,
verbosity = 1L,
suppress_outputs = FALSE,
terminal_run = FALSE,
accuracy_vars = NULL,
max_retries = 3L,
retry_adjust = 0.5,
chart = c("log", "percent"),
error_norm = c("max", "rms"),
controller = c("std", "pi"),
scope = c("pct", "all"),
h_init = NULL,
guard = NULL,
...
)
Arguments
cmf_path |
Character length 1, path to the CMF file
generated by |
solution_method |
The method: |
steps |
Integer length 1 (default |
eps_tolerance |
Numeric length 1 (default |
adaptive |
Character length 1.
|
matrix_method |
Character of length 1, matrix solution
method (default is
|
n_tasks |
Integer length 1 (default is |
n_threads |
Integer length 1 (default |
precision |
Character length 1, |
n_subintervals |
Integer length 1 (default is |
verbosity |
Integer length 1, |
suppress_outputs |
Logical length 1 (default is |
terminal_run |
Logical length 1 (default is |
accuracy_vars |
Character vector of variable names
(default |
max_retries |
Integer length 1 (default |
retry_adjust |
Numeric length 1 in (0, 1) (default
|
chart |
Character length 1, the coordinates the stages
are combined in. |
error_norm |
Character length 1. Whether the worst
element ( |
controller |
Character length 1, the step-size rule:
|
scope |
Character length 1, which elements the accept
test looks at: |
h_init |
Numeric length 1 in (0, |
guard |
Numeric length 1 greater than 1 (default |
... |
Named extras, as |
Value
As ems_solve().
References
Schiffmann, F. (2022), "Runge Kutta integrators for fast and accurate solutions in GEMPACK", GEMPACK Software, Centre of Policy Studies, Victoria University, Melbourne (14 April).
Munthe-Kaas, H. (1999), "High order Runge-Kutta methods on manifolds", Applied Numerical Mathematics, vol. 29, pp. 115-127.
Dormand, J.R. and Prince, P.J. (1980), "A family of embedded Runge-Kutta formulae", Journal of Computational and Applied Mathematics, vol. 6, pp. 19-26.
Bogacki, P. and Shampine, L.F. (1989), "A 3(2) pair of Runge-Kutta formulas", Applied Mathematics Letters, vol. 2, pp. 321-325.
See Also
Examples
## Not run:
# The following examples require the teems solver to be built.
# See https://teemsphere.github.io/ to get started.
# Adaptive DoPri54 (the defaults):
ems_RK(cmf_path)
# Fixed-step RK4:
ems_RK(cmf_path, solution_method = "RK4", steps = 8L)
## End(Not run)
Compose model results into structured data objects
Description
ems_compose() retrieves and processes results
from a solved model run. Data validation and consistency
checks are performed during composition.
Usage
ems_compose(cmf_path, which = "all", passes = FALSE)
Arguments
cmf_path |
Character length 1, path to the CMF file
generated by |
which |
Character vector of variable length (default
|
passes |
Logical length 1 (default |
Details
Every variable whose pre-simulation level is known
gains the columns pre_level and post_level, plus
change (the ordinary change) for a percent-change variable
or percent_change for a change variable. The level is
known for a variable declared with ORIG_LEVEL= (a
coefficient over exactly the variable's sets, or a number)
and for a levels variable; pre-simulation values come from
the solver's sol.cbin0.
With passes = TRUE, each variable's data.table gains, in
the units of Value where applicable:
-
pass1topass3: the separate solutions, fewest to most steps. -
figures: the significant figures on which the two extrapolations agree (0 to 6,NAwhen both are below 1e-6);levels_figures: the same for the levels value. -
error: the difference between the two extrapolations. -
code: the convergence code, best"XMA"to worst"OD!"; see GEMPACK manual 26.2.3. -
summarized: whether the element counts in the run's accuracy summary:TRUEfor endogenous and backsolved results (of theaccuracy_varsvariables when those are given),FALSEfor exogenous elements, whose values the shock sets.
With subintervals, figures and levels_figures are the
lowest over the subintervals and code the worst; pass1
to pass3 and error come from the last subinterval alone,
each pass compounded onto the extrapolated result of the
subintervals before it. The per-variable summary,
attr(output, "accuracy"), has elements, summarized,
min_figures, min_levels_figures (a zero result counts as
6), share_figures, share_levels_figures (share at
accuracy_figures or more, see ems_option_set()),
worst_code and max_error.
Value
A tibble with columns "name", "label", "type", and
"dat" (a list-column of data.tables) containing model
results. For runs solved with an embedded Runge-Kutta method
("BoSha32", "DoPri54"; see ems_solve()) each
variable's data.table carries an additional error_estimate
column: the solver's component-by-component estimate of the
cumulative solution error, |delta| / max(1, |Value|).
Sorting on error_estimate ranks the results by how settled
they are; the estimate is an indicator, not a bound on the
error.
See Also
ems_solve() for solving the CGE model.
Examples
## Not run:
# The following examples require that a model run has taken
# place. See https://teemsphere.github.io/ to get started.
# Return all variables and coefficients
outputs <- ems_compose(cmf_path)
# Return specific variables and/or coefficients by name
outputs <- ems_compose(cmf_path, c("qfd", "EVFP"))
# Add the three separate solutions of a Gragg run
outputs <- ems_compose(cmf_path, "qgdp", passes = TRUE)
## End(Not run)
Prepare a custom shock
Description
Prepares heterogeneous shocks specified on a
tuple-by-tuple basis, in the variable's own form (percentage
or ordinary change). Only the tuples present in input are
shocked.
Usage
ems_custom_shock(var, input)
Arguments
var |
Character of length 1, the variable to be shocked. |
input |
Path to a CSV file, or a data frame or data frame
extension (e.g., tibble, data.table). Must contain one
column named |
Value
A list object with shock configuration to be passed
to the shock argument of ems_deploy().
See Also
ems_deploy() for loading the output of this
function, ems_swap() for changing the standard model
closure.
Examples
# Set elements
sectors <- c("crops", "food", "livestock", "mnfcs", "svces")
regions <- c("asia", "eit", "lam", "maf", "oecd")
time_steps <- 0:7
# Create data frame
aoall_data <- expand.grid(ACTSa = sectors,
REGr = regions,
ALLTIMEt = time_steps)
aoall_data$Value <- runif(nrow(aoall_data))
head(aoall_data)
# Assign values to a model variable (aoall)
ems_custom_shock("aoall", aoall_data)
# In the case of temporally dynamic models, chronological
# year(s) specified by the column "Year" may be used instead
# of the the time set.
pop_data <- data.frame(REGr = "asia",
Year = 2023:2030)
pop_data$Value <- runif(nrow(pop_data))
pop_data
ems_custom_shock("pop", pop_data)
Load and prepare data inputs
Description
Loads input files, aggregates basedata and
parameters according to set mappings, and returns prepared
data for ems_deploy(). Accepts GTAP HAR files and
objects generated by GTAP_convert() as inputs, or a
single HAR file holding a complete non-GTAP database (see
Details).
Usage
ems_data(
dat_input,
par_input = NULL,
set_input = NULL,
time_steps = NULL,
par_weights = "value",
...
)
Arguments
dat_input |
Character vector of length 1, file name in
working directory or path to a data input containing
basedata coefficient data, or the corresponding "dat" list
object generated by |
par_input |
Character vector of length 1, file name in
working directory or path to a data input containing
parameter coefficient data, or the corresponding "par" list
object generated by |
set_input |
Character vector of length 1, file name in
working directory or path to a data input containing set
elements and attributes, or the corresponding "set" list
object generated by |
time_steps |
Integer vector of variable length (default
is |
par_weights |
Character vector (default is
An unnamed element sets the method for every weighted
parameter; elements named after a parameter header (e.g.
|
... |
A named pairlist assigning set mappings to model sets that are explicitly read (not constructed via any set operation defined in the model file). Set mappings can be selected from a range of internally available options or provided by the user.
See teems-mappings for internally available mappings and formatting for user-provided mappings. |
Details
Set names passed via ... must match set names as
they appear in the database. Only sets requiring aggregation
need to be specified. Unspecified sets whose elements are
fully covered by a provided mapping are derived
automatically. Any elements not covered by a provided
mapping are passed through without aggregation.
Single-file route: when only dat_input is given, the HAR
file is taken as a complete database in its own right (for
example the ORANI-G basedata.har). Every character header
with distinct entries becomes a set named after its header,
every real header becomes a coefficient whose dimensions are
the set labels stored in the file, and the sets are passed
through without aggregation. No database version is read and
no set mappings may be supplied on this route.
On the GTAP-E and GTAP-Power layers ELFVAEN (EFVE) follows
FlexAgg's aggpar programs: coal, oil and gas mining are
recalibrated to the target supply elasticities (SPLY),
assuming as Burniaux and Truong (2002) do a Leontief top
nest and perfectly elastic supply of every input other than
the natural resource, and the other fuels take 1. Two
results are then overridden, reported when verbose is on,
and listed in the metadata: a recalibrated value below 0.1,
which a natural-resource rent too small to carry its target
produces, keeps the aggregated member value; and an
aggregate whose members all carry the database placeholder
1e-6 (the technologies without energy inputs) takes 1.
Value
A list of data.tables ready for input into the .data
argument of ems_deploy()
See Also
ems_deploy() for loading the output of this
function. GTAP_convert() for converting GTAP HAR files
and data formats.
Examples
## Not run:
# The following examples require input data. See
# https://teemsphere.github.io/ to get started.
# Single-file database (non-GTAP), no aggregation
orani_data <- ems_data("oranig/basedata.har")
# Data for a static model using internal mappings
v7_data <- ems_data("v7_data/gsdfdat.har",
"v7_data/gsdfpar.har",
"v7_data/gsdfset.har",
REG = "AR5",
ACTS = "food",
ENDW = "labor_diff")
# The same aggregation with FlexAgg's value weights for the
# import-sourcing elasticities
v7_value <- ems_data("v7_data/gsdfdat.har",
"v7_data/gsdfpar.har",
"v7_data/gsdfset.har",
REG = "AR5",
ACTS = "food",
ENDW = "labor_diff",
par_weights = c(ESBM = "share"))
# Data for an intertemporal model with explicit time steps
int_data <- ems_data("v7_data/gsdfdat.har",
"v7_data/gsdfpar.har",
"v7_data/gsdfset.har",
REG = "WB23",
ACTS = "services",
ENDW = "labor_agg",
time_steps = c(0, 1, 2, 4, 6, 8, 10, 15))
# Data for an intertemporal model with chronological time
# steps and a user-provided mapping for the ENDW set
int_data <- ems_data("v7_data/gsdfdat.har",
"v7_data/gsdfpar.har",
"v7_data/gsdfset.har",
REG = "R32",
ACTS = "medium",
ENDW = "user/endowment/mapping.csv",
time_steps = c(2023, 2025, 2027, 2030, 2035))
## End(Not run)
Validate and write all model inputs
Description
Validates all data and model inputs, processes
shocks and closure swaps, and writes the input files
required by ems_solve().
Usage
ems_deploy(
.data,
model,
shock = NULL,
swap_in = NULL,
swap_out = NULL,
shock_file = NULL,
write_coefficients = FALSE
)
Arguments
.data |
A list of data.tables generated by
|
model |
A tibble generated by |
shock |
A |
swap_in |
A character vector of variable length, list
generated by |
swap_out |
A character vector of variable length, list
generated by |
shock_file |
A character vector length 1 (default
|
write_coefficients |
Logical of length 1 (default
|
Value
Path to the CMF file, to be passed to ems_solve().
See Also
ems_data() for loading and preparing data inputs.
ems_model() for parsing and modifying model and closure
files. ems_uniform_shock(), ems_custom_shock(), and
ems_scenario_shock() for preparing shocks.
ems_swap() for preparing closure swaps. ems_solve()
for utilizing the output of this function.
Examples
## Not run:
# The following examples require input data. See
# https://teemsphere.github.io/ to get started.
# Uniform shock: 1% real GDP growth in every region
shock <- ems_uniform_shock("qgdp", value = 1)
# Full variable swap, qgdp for aoreg (GDP target, endogenous
# productivity)
cmf_path <- ems_deploy(
.data = dat,
model = model,
shock = shock,
swap_in = "qgdp",
swap_out = "aoreg"
)
# Partial variable swap (element "row" of set REG with index r)
yp_row <- ems_swap("yp", REGr = "row")
dppriv_row <- ems_swap("dppriv", REGr = "row")
# Swap part of yp for part of dppriv; qgdp for aoreg
cmf_path <- ems_deploy(
.data = dat,
model = model,
shock = shock,
swap_in = list(yp_row, "qgdp"),
swap_out = list(dppriv_row, "aoreg")
)
## End(Not run)
Write teems example models and scripts to file
Description
The teems package includes example models and scripts. This function facilitates access to both, allowing new users to immediately peruse compatible models or generate scripts containing a range of package features.
Usage
ems_example(
model,
path,
type = c("model_files", "scripts"),
dat_input = NULL,
par_input = NULL,
set_input = NULL
)
Arguments
model |
Character vector of length 1, name of model. Options include:
|
path |
Character vector of length 1. Directory where files will be written. |
type |
Character vector of length 1, (default is
|
dat_input |
Character vector of length 1 (default is
|
par_input |
Character vector of length 1 (default is
|
set_input |
Character vector of length 1 (default is
|
Value
For type = "model_files": a named character vector
with elements model_file and closure_file. For type = "scripts": a character vector of paths to the written
script files.
See Also
GTAP_convert() for converting GTAP HAR files and
data formats.
Examples
# Retrieve GTAPv7 model files
ems_example("GTAPv7", tempdir())
## Not run:
# The following examples require input data. See
# https://teemsphere.github.io/ to get started.
# Generate GTAPv7 example scripts
ems_example(model = "GTAPv7",
path = "path/to/example/scripts",
type = "scripts",
dat_input = "v7_data/gsdfdat.har",
par_input = "v7_data/gsdfpar.har",
set_input = "v7_data/gsdfset.har")
# Generate GTAP-RE example scripts
ems_example(model = "GTAP-RE",
path = "path/to/example/scripts",
type = "scripts",
dat_input = "v7_data/gsdfdat.har",
par_input = "v7_data/gsdfpar.har",
set_input = "v7_data/gsdfset.har")
# Generate GTAP-AEZ example scripts (a GTAP-AEZ database is
# required; ems_data() prepares its AEZ layer automatically)
ems_example(model = "GTAP-AEZ",
path = "path/to/example/scripts",
type = "scripts",
dat_input = "aez_data/gsdfdat.har",
par_input = "aez_data/gsdfpar.har",
set_input = "aez_data/gsdfset.har")
# Generate GTAP-E example scripts (a GTAP-E database is required;
# ems_data() prepares its energy layer automatically)
ems_example(model = "GTAP-E",
path = "path/to/example/scripts",
type = "scripts",
dat_input = "e_data/gsdfdat.har",
par_input = "e_data/gsdfpar.har",
set_input = "e_data/gsdfset.har")
# Generate GTAP-EP example scripts (a GTAP-Power database is
# required; ems_data() prepares its energy and power layer
# automatically)
ems_example(model = "GTAP-EP",
path = "path/to/example/scripts",
type = "scripts",
dat_input = "power_data/gsdfdat.har",
par_input = "power_data/gsdfpar.har",
set_input = "power_data/gsdfset.har")
# Generate GTAPv6 example scripts from a v7 format database
converted <- GTAP_convert(dat_har = "v7_data/gsdfdat.har",
par_har = "v7_data/gsdfpar.har",
set_har = "v7_data/gsdfset.har",
target = "GTAPv6")
ems_example(model = "GTAPv6",
path = "path/to/example/scripts",
type = "scripts",
dat_input = converted$dat,
par_input = converted$par,
set_input = converted$set)
## End(Not run)
Parse and modify model and closure files
Description
Parses the model and closure files, conducts pre-deployment checks, and carries out specified modifications.
Usage
ems_model(
model_file,
closure_file,
backsolve = NULL,
ignore_condense = FALSE,
...
)
Arguments
model_file |
Character vector length 1, path to a TABLO file with .tab extension. See teems-models for vetted models and compatible Tablo file formatting. |
closure_file |
Character vector length 1, path to a closure file with .cls extension. See teems-models for closure file formatting. |
backsolve |
Character vector of variable length (default
is |
ignore_condense |
Logical length 1 (default is |
... |
A named pairlist assigning values to model coefficients. Name must match a coefficient declared in the model file. Value may be a length-1 numeric, a data frame or data frame extension (e.g., tibble, data.table), or a path to a CSV file. |
Details
If a length-1 numeric is supplied via ..., this
value is applied uniformly across all tuples for that
coefficient. For heterogeneous values, data frame and CSV
inputs must contain a Value column and one column per set
index using the model-specific naming convention (set name
concatenated with its index letter, e.g., REGr, COMMc).
Inputs are subject to structure checks against the set
aggregations specified in ems_data() and all tuples must
be present.
Value
A tibble comprising parsed model statements to be
passed to the model argument of ems_deploy().
See Also
ems_example() for writing teems example models
and scripts to file. ems_deploy() for loading the output
of this function as well as conducting closure swaps.
Examples
# Retrieve the static and the intertemporal example models
GTAPv7 <- ems_example("GTAPv7", tempdir())
GTAP_RE <- ems_example("GTAP-RE", tempdir())
# Simple static model without condensation
ems_model(GTAPv7[["model_file"]],
GTAPv7[["closure_file"]],
ignore_condense = TRUE)
# Construct data frame
sectors <- c("crops", "food", "livestock", "mnfcs", "svces")
regions <- c("usa", "chn", "row")
time_steps <- 0:5
SUBPAR <- expand.grid(COMMc = sectors,
REGr = regions,
ALLTIMEt = time_steps)
SUBPAR$Value <- runif(nrow(SUBPAR))
# Model load with:
# 1) uniform numeric value applied to KAPPA coefficient
# 2) heterogeneous values allocated to SUBPAR via data frame
ems_model(model_file = GTAP_RE[["model_file"]],
closure_file = GTAP_RE[["closure_file"]],
KAPPA = 0.03,
SUBPAR = SUBPAR)
Get default package options
Description
ems_option_get() returns default package
options. If name is NULL (the default), all option
values are returned as a list.
Usage
ems_option_get(name = NULL)
Arguments
name |
Name of the option for which to retrieve a value. One of:
|
Value
If name is NULL, a named list of all current
option values. Otherwise, the value of the requested option.
See Also
ems_option_set() for setting package options.
ems_option_reset() for resetting package options.
Examples
# Retrieve all options values
ems_option_get()
# Retrieve option value for `ndigits`
ems_option_get("ndigits")
Reset to default package options
Description
ems_option_reset() resets all package options
to default values.
Usage
ems_option_reset()
Value
invisible(NULL), called for its side effects.
See Also
ems_option_set() for setting package options.
ems_option_get() for retrieving package options.
Examples
# Set multiple options
ems_option_set(verbose = FALSE, ndigits = 8)
# Retrieve modified option value for `verbose`
ems_option_get("verbose")
# Reset options to default values
ems_option_reset()
# Retrieve default option value for `verbose`
ems_option_get("verbose")
Set advanced package options
Description
ems_option_set() allows the user to customize
advanced options.
Usage
ems_option_set(
tempdir = NULL,
verbose = NULL,
ndigits = NULL,
accuracy_threshold = NULL,
accuracy_figures = NULL,
accuracy_criterion = NULL,
required_figures = NULL,
full_exclude = NULL,
check_shock_status = NULL,
timestep_header = NULL,
n_timestep_header = NULL,
docker_tag = NULL,
assertions = NULL,
range_test_initial = NULL,
range_test_updated = NULL,
random_seed = NULL,
refine = NULL,
converge = NULL
)
Arguments
tempdir |
A character vector length 1. Default is what is
returned by |
verbose |
Logical of length 1 (default is |
ndigits |
Integer (default is |
accuracy_threshold |
Numeric length 1 (default |
accuracy_figures |
Integer length 1 from 1 to 6 (default
|
accuracy_criterion |
Character length 1 (default
|
required_figures |
Integer length 1 from 1 to 6 (default
|
full_exclude |
A character vector of variable length
(default is |
check_shock_status |
Logical of length 1 (default is
|
timestep_header |
A character vector length 1 (default is
|
n_timestep_header |
A character vector length 1 (default
is |
docker_tag |
Character length 1 (default |
assertions |
Character length 1, |
range_test_initial |
Character length 1, |
range_test_updated |
Character length 1, |
random_seed |
Integer (default is |
refine |
Logical length 1 (default |
converge |
Logical length 1 (default |
Value
invisible(NULL), called for its side effects.
See Also
ems_option_get() for retrieving package options.
ems_option_reset() for resetting package options.
Examples
# Set multiple options
ems_option_set(verbose = FALSE, ndigits = 8)
# Retrieve value of `tempdir`
ems_option_get("tempdir")
# Reset options to default values
ems_option_reset()
Structural probe of a deployed model
Description
Runs the solver up to the point where the equation system is assembled, without solving, and checks that system. It reports whether the closure is valid, and names the elements at fault when it is not, as well as attempts to judge whether backsolving is advantageous. It also recommends the matrix method, task count and thread count.
Usage
ems_probe(cmf_path, components = TRUE, cores = NULL, memory = NULL, ...)
Arguments
cmf_path |
Character length 1, path to the CMF file
written by |
components |
Logical length 1 (default |
cores |
Integer length 1 or |
memory |
Numeric length 1 or |
... |
Named solver arguments, the same ones |
Details
A probe runs on one task. It takes seconds on a
condensed GTAP model and minutes at a few million
uncondensed equations. A singular system is reported, not
raised as an error: the printed object names the
undetermined variables and the over-constrained equations,
plot(x, type = "dm") locates them and x$defects lists
every element.
Value
A teems_probe object: valid; the structural and
realized (base-data) rank patterns; the defects,
statements and incidence tibbles; components; structure
(the time chain and block partition measured); condense;
recommendation, with its status; and paths. print()
gives the verdict and the recommendation, summary() the
full report and plot.teems_probe() the pictures.
Condensation
Backsolving shrinks the system but densifies the blocks the parallel methods split along; on
GTAP-RE the standard condensation makes "SBBD" runs much
slower. The probe's verdict on the deployment is in
x$condense$verdict:
-
"slower": condensed, with a block partition and either a time chain or more than about 120 thousand condensed equations; try redeploying withoutbacksolve. -
"lu_fine": condensed, with a partition, below that size; threaded"LU"on the condensed system was the fastest measured. -
"faster": condensed, without a partition; the system is"LU"-bound and condensation tends to speed it. -
"candidate": uncondensed,"LU"-bound and a million equations or more;backsolveinems_model()may help. -
"none": no verdict.
Recommendation
From the measured structure, the deploy metadata and a memory model per method, the probe suggests a
matrix method with its tasks and threads for the machine
(the container's, or the cores and memory given). It
prints as a ready-to-paste ems_solve() call and is kept
in x$recommendation. In three cases the probe makes no
recommendation and recommendation$status says why:
"singular", the closure must be fixed first; "no_host",
the container's cores could not be read, so pass cores and
memory; "wont_fit", no method fits in the memory. A
system below 300 thousand equations, the smallest
size measured, is sent to "LU". The rules and the
measurements behind them are in the
solving and
benchmarks
chapters of the manual. ems_probe() is experimental: its rules
come from a limited
set of models and machines, so a different method, task
count or thread count may be faster for yours. Try
alternatives with ems_solve(), and report a suggestion
that is off at
https://github.com/teemsphere/teems/issues.
See Also
ems_deploy() for writing the CMF file;
ems_solve() for the solve; plot.teems_probe().
Examples
## Not run:
# The following examples require the teems solver to be built.
# See https://teemsphere.github.io/ to get started.
probe <- ems_probe(cmf_path)
probe
plot(probe, type = "incidence")
plot(probe, type = "components")
## End(Not run)
Prepare a scenario shock
Description
Prepares a trajectory shock for an intertemporal
model from absolute values: a value per pre-aggregation tuple
and year, in the units of the variable's data (million USD,
persons). At deployment the values are summed over the
aggregation of ems_data(), and each year's aggregated value
becomes the percentage change from the base-year value (the
ordinary change for a variable declared (change)). The same
input therefore serves any aggregation. Because the values
are summed, scenario shocks suit additive variables, values
and quantities.
By default input must hold every pre-aggregation tuple of
the variable in every year. With partial = TRUE it may hold
only the tuples behind some aggregated tuples, each complete:
an aggregated tuple covered in part stops the deployment by
name, and the aggregated tuples not covered keep a zero
change. See the
scenario
shocks chapter of the manual for a worked population
trajectory.
Usage
ems_scenario_shock(var, input, partial = FALSE)
Arguments
var |
Character of length 1, the variable to be shocked. |
input |
Path to a CSV file, or a data frame or data frame
extension (e.g., tibble, data.table), with a |
partial |
Logical of length 1 (default |
Value
A list object with shock configuration to be passed
to the shock argument of ems_deploy().
See Also
ems_deploy() for loading the output of this
function. ems_custom_shock() for shocks given directly as
percentage or ordinary changes at the model's aggregation.
Examples
# A trajectory for part of the world: three pre-aggregation
# regions that the aggregation of ems_data() groups into one
# region, in millions, base year 2017 first. At deployment the
# three are summed and each later year becomes the percentage
# change from 2017. Without partial = TRUE every region of the
# database would have to be present; the manual's population
# chapter builds such a trajectory from the POP header.
pop <- expand.grid(REGr = c("aus", "nzl", "xoc"),
Year = 2017:2020,
stringsAsFactors = FALSE)
pop$Value <- c(24.6, 4.8, 1.9) * 1.015^(pop$Year - 2017)
pop
ems_scenario_shock("pop", pop, partial = TRUE)
# The same from a CSV file
csv <- tempfile(fileext = ".csv")
write.csv(pop, csv, row.names = FALSE)
ems_scenario_shock("pop", csv, partial = TRUE)
Configure and solve model
Description
Calls the
teems-solver
Docker image to solve the model's nonlinear equation system.
Runs singularity, accuracy, and error checks on the results
and structures outputs with ems_compose().
Usage
ems_solve(
cmf_path,
solution_method = c("Gragg", "Johansen", "Euler", "Midpoint", "RK2", "Heun", "RK4",
"BoSha32", "DoPri54"),
matrix_method = c("LU", "DBBD", "SBBD", "NDBBD"),
n_subintervals = 1L,
steps = NULL,
n_tasks = 1L,
n_threads = 1L,
precision = c("single", "double"),
verbosity = 1L,
suppress_outputs = FALSE,
terminal_run = FALSE,
accuracy_vars = NULL,
...
)
Arguments
cmf_path |
Character length 1, path to the CMF file
generated by |
solution_method |
The solution method to be used, default
is
|
matrix_method |
Character of length 1, matrix solution
method (default is
|
n_subintervals |
Integer length 1 (default is |
steps |
Integer (default is |
n_tasks |
Integer length 1 (default is |
n_threads |
Integer length 1 (default |
precision |
Character length 1, |
verbosity |
Integer length 1, |
suppress_outputs |
Logical length 1 (default is |
terminal_run |
Logical length 1 (default is |
accuracy_vars |
Character vector of variable names
(default |
... |
Additional named solver arguments; anything else is
an error, never a silently ignored flag. Effective values of
recorded flags land in Expert solver flags, with the solver default applied when a flag is absent:
Runge-Kutta step controls: MA48 workspace initial guesses, integer percents of the system
nonzeros. When omitted, a previous run of the same
deployment warm-starts them from its recorded
|
Value
A tibble of model output variables and coefficients.
The CMF path, invisibly, if suppress_outputs = TRUE; pass
it to ems_compose(). Instructions for terminal execution
if terminal_run = TRUE.
Solving
The model is written in linearized
(percentage-change) form, and the shock is applied as a path
from the base data, which is the initial solution, to the
post-shock equilibrium (Pearson 1991). Each step along the
path solves one or more linear systems in the model's
Jacobian (a Gragg run of N steps makes N + 1 passes, a
"DoPri54" step 7 stages) and then updates the data.
"Johansen" takes that path in a single step, so its error
grows with the size of the shock. The multistep methods
divide the path into smaller steps, so the linearization
error shrinks as the number of steps rises, and the
extrapolating methods then remove most of the error that
remains. Computing time grows with the total number of
steps, and with n_subintervals, since each subinterval
repeats the full solve on its share of the shock. A run can
be reproduced from its record in sol.stats.json.
Accuracy
The extrapolating methods solve at three
step counts, and the agreement between the three solutions
gives an accuracy summary over the endogenous results, and
another over the values read from data files and updated. By
default the measure is the share of nonzero results whose
levels values are accurate to at least four significant
figures (results judged zero, both extrapolations below
1e-6, are counted apart). A percent-change result usually
has more accurate figures in its levels value than in the
percentage itself. The accuracy_criterion and
accuracy_figures options switch to the updated data or
both summaries and change the figures required. A warning is
given when the share falls below the accuracy_threshold
option (default 80%, see ems_option_set()), and both
summaries are written to model_diagnostics.txt in the run
directory. When this happens, raise n_subintervals first:
a few steps over several subintervals beat many steps over
one, and a midpoint instability is cured by restarting the
integrator, not by more steps (GEMPACK manual 26.1;
Schiffmann 2022). More steps (for example steps = c(4L, 6L, 8L)) help while the totals stay modest. Adaptive
"DoPri54" estimates the error of every result (see
ems_RK()). With one or two step counts there is no
estimate. If adding steps stops improving accuracy, the run
has reached the rounding limit of single precision, and
precision = "double" is the remedy.
Solution method
The default "Gragg" with c(2L, 4L, 6L) suits most static policy shocks. "Johansen" is a
quick check that a new model and closure run, but its
results should not be reported. Shocks that drive a CES or
CET share close to zero, or a variable close to -100%, can
make the midpoint methods unstable (Schiffmann 2022). In
those cases use "Euler", which may still converge slowly,
or adaptive "DoPri54" or "BoSha32", whose robustness
exceeds Euler's (Schiffmann 2022); a shock of exactly
-100% needs "Midpoint" or "Euler". A single step
count, without extrapolation, suits models whose updates
must follow the steps themselves.
Size, matrix method and resources
The linear system
has one row for each endogenous variable element left after
condensation. Its size grows with the number of regions
times the number of commodities, and for intertemporal
models it also grows with the number of periods. "LU"
factorizes the whole system at once. It works for every
model and is usually best for static models, with
n_threads set to the available cores. The bordered methods
divide the system into blocks that are solved in parallel
and joined through a smaller border system.
With a bordered method, n_tasks is the number of processes
that share the blocks, and n_threads is the number of
threads each process runs. n_tasks * n_threads should not
exceed the available cores. ems_probe() measures a
deployed model and the machine, then recommends
matrix_method, n_tasks and n_threads. Treat its
recommendation as a starting point.
References
Pearson, K.R. (1991), "Solving Nonlinear Economic Models Accurately via a Linear Representation", Impact Project Preliminary Working Paper No. IP-55, Monash University (revised June 2002).
Horridge, J.M., Jerie, M., Mustakinov, D. and Schiffmann, F. (2024), GEMPACK manual (documents Release 12.2), GEMPACK Software, Centre of Policy Studies, Victoria University, Melbourne, ISBN 978-1-921654-34-3. https://ideas.repec.org/p/cop/wpaper/gpman.html
Schiffmann, F. (2022), "Runge Kutta integrators for fast and accurate solutions in GEMPACK", GEMPACK Software, Centre of Policy Studies, Victoria University, Melbourne (14 April).
Van Ha, P. and Kompas, T. (2016), "Solving intertemporal CGE models in parallel using a singly bordered block diagonal ordering technique", Economic Modelling, vol. 52, pp. 3-12. doi:10.1016/j.econmod.2015.07.011
Van Ha, P., Kompas, T., Nguyen, H.T.M. and Long, C.H. (2017), "Building a better trade model to determine local effects: A regional and intertemporal GTAP model", Economic Modelling, vol. 67, pp. 102-113. doi:10.1016/j.econmod.2016.10.015
Kompas, T. and Van Ha, P. (2019), "The 'curse of dimensionality' resolved: The effects of climate change and trade barriers in large dimensional modelling", Economic Modelling, vol. 80, pp. 103-110. doi:10.1016/j.econmod.2018.08.011
HSL (2026), A collection of Fortran codes for large scale scientific computation. https://www.hsl.rl.ac.uk/
See Also
ems_deploy() for generating "cmf_path".
solve_in_situ() for calling the solver on existing input
files. ems_compose() for structuring data when
"suppress_outputs" or "terminal_run" is TRUE.
ems_option_set() for the severities of TAB Assertion
failures and declared-range violations (assertions,
range_test_initial, range_test_updated), and for the
refinement step of "DBBD" solves (refine).
Examples
## Not run:
# The following examples require the teems solver to be built.
# See https://teemsphere.github.io/ to get started.
# Solving a static model with Gragg 2-4-6 (the default):
ems_solve(cmf_path)
# A quick one-step approximation:
ems_solve(cmf_path, solution_method = "Johansen")
# Solving a dynamic model with the SBBD method:
ems_solve(cmf_path,
solution_method = "Gragg",
matrix_method = "SBBD",
n_tasks = 6)
## End(Not run)
Prepare closure swaps
Description
Prepares a closure swap for input into the
swap_in or swap_out arguments of ems_deploy().
Usage
ems_swap(var, ...)
Arguments
var |
Character of length 1, model variable to swap. |
... |
Optional named arguments restricting the swap to a
subset of variable elements. Each name must use the
model-specific set-index format (set name concatenated with
its index letter, e.g.,
|
Details
ems_swap() return values have no purpose used in
isolation. The closure provided to the closure_file
argument of ems_model() will be used if no swaps are
specified. Note that full variable swaps can be directly
inputted as a character string in the "swap_in" and
"swap_out" arguments of ems_deploy().
Swaps "in" (joining the list of exogenous variables) and swaps "out" (leaving it) are reconciled together rather than in a fixed order: each tuple ends exogenous or endogenous by the net of the swaps that name it, so a variable may be swapped in whole and a slice of it swapped back out, or a swap reversed by its mirror. Swaps are rejected only when no order of them is valid on the closure, such as a tuple swapped in twice or a endogenous variable designated for a swap out.
A closure must leave as many endogenous variable elements as
there are equations, so in a working closure, every element
swapped in needs one swapped out; ems_deploy() aborts
when a closure is invalid.
Value
A list of class "full" or "partial" and "single"
or "multi" containing the swap specification. Intended for
use as swap_in or swap_out in ems_deploy().
See Also
ems_model() for parsing and modifying model and
closure files. ems_deploy() for loading the output of
this function.
Examples
# Full variable swaps
ems_swap("tfd") # out
ems_swap("qfd") # in
# Partial variable swaps with uniform "PROD_COMM" set
# application (note distinction between "REGr" and "REGs") in
# the classic GTAP model (version 6.2)
ems_swap("tfd", TRAD_COMMi = "food", REGr = "chn") # out
ems_swap("qfd", TRAD_COMMi = "food", REGs = "chn") # in
# Partial variable, multiple element swaps with uniform "ACTS"
# set application in the standard GTAP model (version 7.0).
ems_swap("tfd", COMMc = c("food", "crops"), REGr = "usa") # out
ems_swap("qfd", COMMc = c("food", "crops"), REGr = "usa") # in
# Valid subsets may also be selected.
ems_swap("txs", COMMc = "NMRG", ALLTIMEt = "FWDTIME") # out
ems_swap("qxs", COMMc = "NMRG", ALLTIMEt = "FWDTIME") # in
Prepare a uniform shock
Description
Prepares a uniform shock to be implemented as a single value uniformly across all or a subset of variable tuples, in the variable's own form: a percentage change for a percent-change variable, an ordinary change for a change variable.
Usage
ems_uniform_shock(var, value, ...)
Arguments
var |
Character of length 1, the variable to be shocked. |
value |
Numeric length 1, value of the shock in the variable's own form (percentage or ordinary change). |
... |
Optional named arguments restricting the shock to a
subset of the variable's elements. Each name must use the
model-specific set-index format (set name concatenated with
its index letter, e.g., |
Value
A list object with shock configuration to be passed
to the shock argument of ems_deploy().
See Also
ems_deploy() for loading the output of this
function. ems_swap() for changing the standard model
closure.
Examples
# Full uniform: 2% shock imposed on all afeall tuples
ems_uniform_shock(var = "afeall", value = 2)
# Partial uniform by element: applied only to the "chn"
# element in set REGr (REG). Note that set designations must
# consist of the concatenation of the standard set (e.g., REG)
# and variable-specific index (e.g., r).
ems_uniform_shock(var = "afeall",
REGr = "chn",
value = 2)
# Partially uniform by subset and element: applied to "chn"
# and "usa" across the MARG and FWDTIME subsets.
ems_uniform_shock(var = "qxs",
COMMc = "MARG",
REGs = c("chn", "usa"),
ALLTIMEt = "FWDTIME",
value = -1)
Plot a structural probe
Description
Visualizations of a ems_probe() result:
-
"incidence": the equation-system structure — a spy-style matrix of equation statements (rows, declaration order) by referenced variables (columns, first-appearance order), shaded by element-level incidence weight. -
"dm": the coarse Dulmage-Mendelsohn localization of a structurally singular system — the under-, well- and over-determined blocks to scale (only available when the probe found defects). -
"components": the simultaneous components of the system, the groups of equations that must be solved together: their sizes, and the equation statements of the largest (requirescomponents = TRUE).
Usage
## S3 method for class 'teems_probe'
plot(x, type = c("incidence", "dm", "components"), max_labels = 60L, ...)
Arguments
x |
A |
type |
Character length 1: |
max_labels |
Integer length 1 (default |
... |
Unused. |
Value
The input, invisibly. Base-graphics side effects; the
underlying tibbles (x$incidence, x$components, pattern blocks) are
exposed for custom plotting.
Configure and solve model in-situ
Description
Calls the
teems-solver
Docker image directly with user-supplied input files,
bypassing the ems_data() / ems_model() /
ems_deploy() pipeline. All input files must be provided
in their final form.
Usage
solve_in_situ(
...,
model_dir,
model_file,
closure_file,
shock_file,
ignore_condense = FALSE,
solution_method = c("Gragg", "Johansen", "Euler", "Midpoint", "RK2", "Heun", "RK4",
"BoSha32", "DoPri54"),
matrix_method = c("LU", "DBBD", "SBBD", "NDBBD"),
n_subintervals = 1L,
steps = NULL,
n_tasks = 1L,
n_threads = 1L,
precision = c("single", "double"),
verbosity = 1L,
suppress_outputs = FALSE,
terminal_run = FALSE,
accuracy_vars = NULL,
solver_args = NULL
)
Arguments
... |
Named arguments corresponding to input files
necessary for an in-situ model run. Names must correspond to
"File" statements within the model Tablo file. Values
correspond to file paths where these files are found. No
checks or modifications are conducted on input files used in
this manner. All model declared input files as well as
|
model_dir |
Character of length 1, base directory where input files will be copied (if not all already present) and model outputs will be written. |
model_file |
Character vector length 1, path to a TABLO file with .tab extension. See teems-models for vetted models and compatible Tablo file formatting. |
closure_file |
Character vector length 1, path to a closure file with .cls extension. See teems-models for closure file formatting. |
shock_file |
A character vector length 1, path to a file with .shf extension representing a fully prepared shock file. No checks or modifications are carried out on this file. |
ignore_condense |
Logical length 1 (default is |
solution_method |
The solution method to be used, default
is
|
matrix_method |
Character of length 1, matrix solution
method (default is
|
n_subintervals |
Integer length 1 (default is |
steps |
Integer (default is |
n_tasks |
Integer length 1 (default is |
n_threads |
Integer length 1 (default |
precision |
Character length 1, |
verbosity |
Integer length 1, |
suppress_outputs |
Logical length 1 (default is |
terminal_run |
Logical length 1 (default is |
accuracy_vars |
Character vector of variable names
(default |
solver_args |
Named list (default |
Value
A tibble containing model output variables and
coefficients. Alternatively, if "suppress_outputs" is
TRUE, file path to a CMF file that may be used with
ems_compose().
See Also
ems_solve() for the standard package-supported
solver.
Examples
## Not run:
# The following examples require the teems solver to be built.
# See https://teemsphere.github.io/ to get started.
solve_in_situ(
GTAPDATA = "path/to/dat_file.txt",
GTAPPARM = "path/to/par_file.txt",
GTAPSETS = "path/to/sets_file.txt",
model_dir = "existing/dir/for/model_run",
model_file = "path/to/model_file.tab",
closure_file = "path/to/closure_file.cls",
shock_file = "path/to/shock_file.shf"
)
## End(Not run)