Skip to content

Commit 33796fc

Browse files
committed
fix summary method
1 parent 9801209 commit 33796fc

3 files changed

Lines changed: 93 additions & 22 deletions

File tree

R/Trial.R

Lines changed: 35 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,7 @@ Trial <- R6::R6Class("Trial", #nolint
7878
self$info <- as.list(info)
7979

8080
args <- as.list(formals(self$summary))
81+
8182
args[c("...", "estimates")] <- NULL
8283
private$summary.args_default <- args
8384

@@ -131,7 +132,7 @@ Trial <- R6::R6Class("Trial", #nolint
131132
},
132133

133134
#' @description Get, specify or update the summary.args attribute.
134-
#' @param .args (list or character) named list of arguments to update
135+
#' @param .args (list or character) named list of arguments to update
135136
#' or set. A single or subset of arguments can be retrieved by passing the
136137
#' respective argument names as a character or character vector.
137138
#' @param .reset (logical or character) Reset all or a subset of previously
@@ -513,15 +514,20 @@ Trial <- R6::R6Class("Trial", #nolint
513514
#' the power of both superiority tests (one-sided or two-sided) and
514515
#' non-inferiority tests, together with summary statistics of the
515516
#' different estimators.
517+
#'
518+
#' Arguments provided to this method call take precedence over argument
519+
#' values that have been previously set via ([Trial$args_summary()][Trial]).
520+
#' See the examples for more details.
516521
#' @param level (numeric) significance level
517522
#' @param null (numeric) null hypothesis to test
518523
#' @param ni.margin (numeric) non-inferiority margin
519-
#' @param alternative alternative hypothesis (not equal !=, less <,
520-
#' greater >)
524+
#' @param alternative (character) alternative hypothesis (not equal !=, less
525+
#' <, greater >)
521526
#' @param reject.function Optional function calculating whether to reject
522527
#' the null hypothesis
523-
#' @param true.value Optional true parameter value
524-
#' @param nominal.coverage Width of confidence limits
528+
#' @param true.value (numeric) Optional true parameter value
529+
#' @param nominal.coverage (numeric) Width of confidence limits. The default
530+
#' behavior is to calculate the coverage for the 1 - `level` CI.
525531
#' @param estimates Optional trial.estimates object. When provided, these
526532
#' estimates will be used instead of the object's stored estimates. This
527533
#' allows calculating summaries for different trial results without
@@ -550,20 +556,37 @@ Trial <- R6::R6Class("Trial", #nolint
550556
#'
551557
#' # calculate empirical bias, rmse and coverage for true target parameter
552558
#' trial$summary(estimates = res, true.value = 0)
559+
#'
560+
#' # use args_summary to set default values
561+
#' trial$args_summary(true.value = 0)
562+
#' trial$summary(estimates = res)
563+
#' # arguments to method call preceed arguments that have been set via
564+
#' # args_summary method
565+
#' trial$summary(estimates = res, true.value = 1)
553566
summary = function(level = .05,
554567
null = 0,
555568
ni.margin = NULL,
556569
alternative = "!=",
557570
reject.function = NULL,
558571
true.value = NULL,
559-
nominal.coverage = 0.9,
572+
nominal.coverage = NULL,
560573
estimates = NULL,
561574
...) {
562-
trial_summary(self = self, level = level, null = null,
563-
ni.margin = ni.margin, alternative = alternative,
564-
reject.function = reject.function, true.value = true.value,
565-
nominal.coverage = nominal.coverage, estimates = estimates, ...
566-
)
575+
mc_supplied <- as.list(match.call(expand.dots = FALSE))[-1]
576+
nm_formals_supplied <- setdiff(names(mc_supplied), "...")
577+
call_args <- if (length(nm_formals_supplied)) {
578+
mget(nm_formals_supplied, inherits = FALSE)
579+
} else {
580+
list()
581+
}
582+
if ("..." %in% names(mc_supplied)) call_args <- c(call_args, list(...))
583+
584+
args <- self$args_summary()
585+
args[names(call_args)] <- call_args
586+
587+
if (!("estimates" %in% names(args))) args <- c(args, list(estimates = NULL))
588+
589+
do.call(trial_summary, c(list(self = self), args))
567590
},
568591

569592
#' @description Print method for Trial objects
@@ -714,6 +737,7 @@ trial_summary <- function(self, level, null, ni.margin, alternative,
714737
if (!(alternative %in% c("!=", "<", ">"))) {
715738
rlang::abort('alternative should be one of "!=", "<", ">"')
716739
}
740+
if (is.null(nominal.coverage)) nominal.coverage <- 1 - level
717741

718742
alternative <- gsub(" ", "", tolower(alternative[1]))
719743
q_alpha_cov <- qnorm(1 - (1 - nominal.coverage) / 2) # quantile for

inst/tinytest/test_Trial.R

Lines changed: 34 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -312,7 +312,7 @@ test_args_summary <- function() {
312312
alternative = "!=",
313313
reject.function = NULL,
314314
true.value = NULL,
315-
nominal.coverage = 0.9
315+
nominal.coverage = NULL
316316
)
317317

318318
# arguments are set correctly when using summary.args / test getter
@@ -683,11 +683,15 @@ test_summary <- function() {
683683
expect_true(s[1, "power"] < s2[1, "power"])
684684

685685
# test that nominal coverage around true.value is correctly calculated
686-
s3 <- m$summary(true.value = -.25, nominal.coverage = 0.9)
687-
expect_equal(s3[, "coverage"], 0.9, tolerance = 0.05)
686+
# default behavior is to obtain the coverage for 1 - level
687+
s3 <- m$summary(true.value = -.25)
688+
expect_equal((ss <- s3[, "coverage"]), 0.95, tolerance = 0.05)
689+
s3 <- m$summary(true.value = -.25, nominal.coverage = 0.95)
690+
expect_equal(ss, s3[, "coverage"])
688691
s3 <- m$summary(true.value = -.25, nominal.coverage = 0.5)
689692
expect_equal(s3[, "coverage"], 0.5, tolerance = 0.05)
690693

694+
691695
# test ni.margin; expect power around 5% since true value is -0.25
692696
s <- m$summary(ni.margin = -.25, alternative = ">")
693697
expect_equal(s[1, "power"], 0.05, tolerance = 0.1)
@@ -723,8 +727,8 @@ test_summary <- function() {
723727
s <- m$summary()
724728
expect_equal(rownames(s), c("est1", "est2"))
725729

726-
# Add new test block for estimates parameter
727-
# Test that providing estimates directly works the same as using stored estimates
730+
# Test that providing estimates directly works the same as using stored
731+
# estimates
728732
res2 <- m$run(n = 100, R = 100, p = c(0.5, 0.25))
729733
s1 <- m$summary()
730734
s2 <- m$summary(estimates = res2)
@@ -734,7 +738,6 @@ test_summary <- function() {
734738
s3 <- m$summary(estimates = res2, level = 0.1)
735739
expect_false(identical(s2, s3))
736740

737-
738741
# Test that providing estimates doesn't modify the object's stored estimates
739742
original_estimates <- m$estimates
740743
m$summary(estimates = res2)
@@ -744,5 +747,30 @@ test_summary <- function() {
744747
different_res <- m$run(n = 200, R = 100, p = c(0.5, 0.25)) # Different n
745748
s3 <- m$summary(estimates = different_res)
746749
expect_false(identical(s1, s3)) # Should be different due to different n
750+
751+
# tests for setting default values for summary method with args_summary method
752+
outcome <- function(data, p = c(0.5, 0.25)) {
753+
a <- rbinom(nrow(data), 1, 0.5)
754+
data.frame(a = a, y = rbinom(nrow(data), 1, p[1] * (1 - a) + p[2] * a)
755+
)
756+
}
757+
trial <- Trial$new(outcome, estimators = est_glm())
758+
trial$args_summary(level = 0)
759+
trial$run(n = 100, R = 10)
760+
# verify that method picks up arguments that are set via args_summary
761+
expect_equal(trial$summary()[1, "power"], 0) # needs to be 0 because level = 0
762+
# verify that arguments to method take precedence over set arguments
763+
expect_equal(
764+
(pp <- trial$summary(level = 1)[1, "power"]),
765+
1
766+
) # needs to be 0 because level = 0
767+
# verify that default value of argument can be used
768+
expect_true(pp != trial$summary(level = 0.05)[1, "power"])
769+
# also works with do.call
770+
expect_equal(
771+
pp,
772+
do.call(trial$summary, list(level = 1))[1, "power"]
773+
)
774+
747775
}
748776
test_summary()

man/Trial.Rd

Lines changed: 24 additions & 5 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)