This function allows a series of sampling design settings to be tested on a simulated population. True population values are compared to stratified estimates of abundance using a user-specified number of simulated surveys.

test_surveys(
  sim,
  surveys = expand_surveys(),
  keep_details = 1,
  n_sims = 1,
  n_loops = 100,
  cores = 2,
  export_dir = NULL,
  length_group = "inherit",
  alk_scale = "division",
  progress = TRUE,
  ...
)

resume_test(export_dir = NULL, ...)

Arguments

sim

A simulation object returned by sim_distribution().

surveys

A data.frame or data.table of survey configurations, formatted like the object returned by expand_surveys().

keep_details

Integer. Retain full details for one survey (specified by survey number), and drop the rest to reduce object size.

n_sims

Number of surveys to simulate per design. Large values may consume significant RAM.

n_loops

Number of times to loop sim_survey(). Total number of simulations = n_sims × n_loops. A lower n_sims and higher n_loops combination is more memory efficient but may take longer.

cores

Number of processor cores to use in parallel.

export_dir

Optional directory path to export intermediate results. Useful for resuming later with resume_test(). If NULL, nothing is exported.

length_group

Size of the length frequency bins used for both abundance-at-length calculations and age-length-key construction. By default, this is inherited from the value defined in sim_abundance() via the closure supplied to sim_length ("inherit"). You may also supply a numeric value; however, mismatches in length groupings may cause issues with strat_error() if true vs. estimated groupings are not aligned.

alk_scale

Spatial scale at which to construct and apply age-length keys: "division" or "strat".

progress

Logical. Should progress bar and messages be displayed?

...

Arguments passed on to sim_survey

q

A closure (e.g., sim_logistic()) for simulating catchability at age. Returned values must range between 0 and 1.

trawl_dim

Trawl width and distance (same units as the grid).

resample_cells

Logical. If TRUE, allows grid cells to be resampled. May introduce bias, as depletion is applied at the cell level.

binom_error

Logical. Should binomial error be imposed? If FALSE, stratified estimates at older ages may be biased due to rounding zeros.

min_sets

Minimum number of sets per stratum.

age_sampling

Type of age sampling strategy: "stratified" (default) or "random".

age_length_group

Width of length bins for stratified age sampling. Ignored if age_sampling = "random".

age_space_group

Spatial scale for stratified age sampling. Options: "division" (default), "strat", or "set". Ignored if age_sampling = "random".

custom_sets

A data.table of set locations (same structure as returned by sim_sets()). If NULL, set locations are generated automatically.

Value

The returned object includes:

  • A table of survey designs tested

  • Stratified error results (*_strat_error and *_strat_error_stats)

  • Error statistics:

    • ME: Mean error

    • MAE: Mean absolute error

    • MSE: Mean squared error

    • RMSE: Root mean squared error

  • A summary table of total sample sizes (samp_totals)

Survey and stratified analysis details are dropped for all but one retained survey (via keep_details).

Details

Depending on the number of surveys and simulations, test_surveys() can take a long time to run.

The resume_test() function can be used to resume partial runs. Note: progress bar time estimates may be biased if resuming previously completed iterations.

Internally, this function calls a helper called test_loop() to process each survey simulation.

Caution: When using ... inside resume_test(), be careful not to pass arguments that were not part of the original test_surveys() call, as this could change simulation settings.

Examples

# \donttest{
pop <- sim_abundance(ages = 1:20, years = 1:5) |>
  sim_distribution(grid = make_grid(res = c(10, 10)))

surveys <- expand_surveys(
  set_den = c(1, 2) / 1000,
  lengths_cap = c(100, 500),
  ages_cap = c(5, 20)
)

# Simulate 25 surveys for each of 8 survey designs (low for example speed)
tests <- test_surveys(
  pop, surveys = surveys, keep_details = 1,
  n_sims = 5, n_loops = 5, cores = 1
)
#> 
#> Running simulations...
#> 
#> Compiling results...

library(plotly)
tests$total_strat_error |>
  filter(survey == 8, sim %in% 1:50) |>
  group_by(sim) |>
  plot_ly(x = ~year) |>
  add_lines(y = ~I_hat, alpha = 0.5, name = "estimated") |>
  add_lines(y = ~I, color = I("black"), name = "true") |>
  layout(xaxis = list(title = "Year"),
         yaxis = list(title = "Abundance index"))
plot_total_strat_fan(tests, surveys = 1:8)
plot_length_strat_fan(tests, surveys = 1:8)
plot_age_strat_fan(tests, surveys = 1:8)
plot_age_strat_fan(tests, surveys = 1:8, select_by = "age")
plot_error_surface(tests, plot_by = "rule")
plot_error_surface(tests, plot_by = "samples")
plot_survey_rank(tests, which_strat = "length")
plot_survey_rank(tests, which_strat = "age")
# }