diff --git a/R/class-forecast-binary.R b/R/class-forecast-binary.R index bf4d0b835..190ab5e25 100644 --- a/R/class-forecast-binary.R +++ b/R/class-forecast-binary.R @@ -36,6 +36,7 @@ as_forecast_binary <- function(data, ...) { } #' @rdname as_forecast_binary +#' @inheritParams assert_forecast #' @export #' @method as_forecast_binary default #' @importFrom cli cli_warn @@ -43,6 +44,7 @@ as_forecast_binary.default <- function(data, forecast_unit = NULL, observed = NULL, predicted = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -51,7 +53,7 @@ as_forecast_binary.default <- function(data, predicted = predicted ) data <- new_forecast(data, "forecast_binary") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-multivariate-sample.R b/R/class-forecast-multivariate-sample.R index d445e27e0..ea64d573b 100644 --- a/R/class-forecast-multivariate-sample.R +++ b/R/class-forecast-multivariate-sample.R @@ -53,6 +53,7 @@ as_forecast_multivariate_sample <- function(data, ...) { #' For example, if you have a column `country` and want to define #' a multivariate forecast for several countries at once, you could set #' `joint_across = "country"`. +#' @inheritParams assert_forecast #' @export #' @importFrom cli cli_warn as_forecast_multivariate_sample.default <- function(data, @@ -61,6 +62,7 @@ as_forecast_multivariate_sample.default <- function(data, observed = NULL, predicted = NULL, sample_id = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -72,7 +74,7 @@ as_forecast_multivariate_sample.default <- function(data, data <- set_grouping(data, joint_across) data <- new_forecast(data, "forecast_sample_multivariate") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-nominal.R b/R/class-forecast-nominal.R index 217b25559..a064c4316 100644 --- a/R/class-forecast-nominal.R +++ b/R/class-forecast-nominal.R @@ -47,6 +47,7 @@ as_forecast_nominal <- function(data, ...) { #' @param predicted_label (optional) Name of the column in `data` that denotes #' the outcome to which a predicted probability corresponds to. #' This column will be renamed to "predicted_label". +#' @inheritParams assert_forecast #' @export #' @method as_forecast_nominal default #' @importFrom cli cli_warn @@ -55,6 +56,7 @@ as_forecast_nominal.default <- function(data, observed = NULL, predicted = NULL, predicted_label = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -64,7 +66,7 @@ as_forecast_nominal.default <- function(data, predicted_label = predicted_label ) data <- new_forecast(data, "forecast_nominal") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-ordinal.R b/R/class-forecast-ordinal.R index 4a2c86b28..8dc2c76f1 100644 --- a/R/class-forecast-ordinal.R +++ b/R/class-forecast-ordinal.R @@ -47,6 +47,7 @@ as_forecast_ordinal <- function(data, ...) { #' @param predicted_label (optional) Name of the column in `data` that denotes #' the outcome to which a predicted probability corresponds to. #' This column will be renamed to "predicted_label". +#' @inheritParams assert_forecast #' @export #' @method as_forecast_ordinal default #' @importFrom cli cli_warn @@ -55,6 +56,7 @@ as_forecast_ordinal.default <- function(data, observed = NULL, predicted = NULL, predicted_label = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -64,7 +66,7 @@ as_forecast_ordinal.default <- function(data, predicted_label = predicted_label ) data <- new_forecast(data, "forecast_ordinal") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-point.R b/R/class-forecast-point.R index 8635b25b9..571b498aa 100644 --- a/R/class-forecast-point.R +++ b/R/class-forecast-point.R @@ -24,6 +24,7 @@ as_forecast_point <- function(data, ...) { #' @rdname as_forecast_point +#' @inheritParams assert_forecast #' @export #' @method as_forecast_point default #' @importFrom cli cli_warn @@ -31,6 +32,7 @@ as_forecast_point.default <- function(data, forecast_unit = NULL, observed = NULL, predicted = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -39,7 +41,7 @@ as_forecast_point.default <- function(data, predicted = predicted ) data <- new_forecast(data, "forecast_point") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-quantile.R b/R/class-forecast-quantile.R index 6d6c1bd3d..36a66b713 100644 --- a/R/class-forecast-quantile.R +++ b/R/class-forecast-quantile.R @@ -39,6 +39,7 @@ as_forecast_quantile <- function(data, ...) { #' @param quantile_level (optional) Name of the column in `data` that contains #' the quantile level of the predicted values. This column will be renamed to #' "quantile_level". Only applicable to quantile-based forecasts. +#' @inheritParams assert_forecast #' @export #' @method as_forecast_quantile default #' @importFrom cli cli_warn @@ -47,6 +48,7 @@ as_forecast_quantile.default <- function(data, observed = NULL, predicted = NULL, quantile_level = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -58,19 +60,21 @@ as_forecast_quantile.default <- function(data, unique_q_levels <- sort(unique(data$quantile_level)) level_diffs <- diff(unique_q_levels) if (any(level_diffs <= 1e-10)) { - cli_warn( - "The {.code quantile_level} column in your data - seems to have a rounding issue - (run {.code diff(sort(unique(data$quantile_level)))} to see this. - As {.code scoringutils} does not support arbitrarily fine quantile level - increments, we're going to run {.code round(x, digits = 10)} on - the {.code quantile_level} column." - ) + if (verbose) { + cli_warn( + "The {.code quantile_level} column in your data + seems to have a rounding issue + (run {.code diff(sort(unique(data$quantile_level)))} to see this. + As {.code scoringutils} does not support arbitrarily fine quantile level + increments, we're going to run {.code round(x, digits = 10)} on + the {.code quantile_level} column." + ) + } data$quantile_level <- round(data$quantile_level, digits = 9) } data <- new_forecast(data, "forecast_quantile") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/R/class-forecast-sample.R b/R/class-forecast-sample.R index 5bf50d865..323ebbf3e 100644 --- a/R/class-forecast-sample.R +++ b/R/class-forecast-sample.R @@ -31,6 +31,7 @@ as_forecast_sample <- function(data, ...) { #' @rdname as_forecast_sample #' @param sample_id (optional) Name of the column in `data` that contains the #' sample id. This column will be renamed to "sample_id". +#' @inheritParams assert_forecast #' @export #' @importFrom cli cli_warn as_forecast_sample.default <- function(data, @@ -38,6 +39,7 @@ as_forecast_sample.default <- function(data, observed = NULL, predicted = NULL, sample_id = NULL, + verbose = TRUE, ...) { data <- as_forecast_generic( data, @@ -47,7 +49,7 @@ as_forecast_sample.default <- function(data, sample_id = sample_id ) data <- new_forecast(data, "forecast_sample") - assert_forecast(data) + assert_forecast(data, verbose = verbose) return(data) } diff --git a/man/as_forecast_binary.Rd b/man/as_forecast_binary.Rd index 4938c514d..38f597e8a 100644 --- a/man/as_forecast_binary.Rd +++ b/man/as_forecast_binary.Rd @@ -12,6 +12,7 @@ as_forecast_binary(data, ...) forecast_unit = NULL, observed = NULL, predicted = NULL, + verbose = TRUE, ... ) } @@ -34,6 +35,9 @@ observed values. This column will be renamed to "observed".} \item{predicted}{(optional) Name of the column in \code{data} that contains the predicted values. This column will be renamed to "predicted".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_binary} diff --git a/man/as_forecast_multivariate_sample.Rd b/man/as_forecast_multivariate_sample.Rd index 04e8cf690..cb2008e39 100644 --- a/man/as_forecast_multivariate_sample.Rd +++ b/man/as_forecast_multivariate_sample.Rd @@ -14,6 +14,7 @@ as_forecast_multivariate_sample(data, ...) observed = NULL, predicted = NULL, sample_id = NULL, + verbose = TRUE, ... ) } @@ -50,6 +51,9 @@ predicted values. This column will be renamed to "predicted".} \item{sample_id}{(optional) Name of the column in \code{data} that contains the sample id. This column will be renamed to "sample_id".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_sample} diff --git a/man/as_forecast_nominal.Rd b/man/as_forecast_nominal.Rd index 1af22c78a..2cd64d3e7 100644 --- a/man/as_forecast_nominal.Rd +++ b/man/as_forecast_nominal.Rd @@ -13,6 +13,7 @@ as_forecast_nominal(data, ...) observed = NULL, predicted = NULL, predicted_label = NULL, + verbose = TRUE, ... ) } @@ -39,6 +40,9 @@ predicted values. This column will be renamed to "predicted".} \item{predicted_label}{(optional) Name of the column in \code{data} that denotes the outcome to which a predicted probability corresponds to. This column will be renamed to "predicted_label".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_nominal} diff --git a/man/as_forecast_ordinal.Rd b/man/as_forecast_ordinal.Rd index e6748c011..ed909d8b6 100644 --- a/man/as_forecast_ordinal.Rd +++ b/man/as_forecast_ordinal.Rd @@ -13,6 +13,7 @@ as_forecast_ordinal(data, ...) observed = NULL, predicted = NULL, predicted_label = NULL, + verbose = TRUE, ... ) } @@ -39,6 +40,9 @@ predicted values. This column will be renamed to "predicted".} \item{predicted_label}{(optional) Name of the column in \code{data} that denotes the outcome to which a predicted probability corresponds to. This column will be renamed to "predicted_label".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_ordinal} diff --git a/man/as_forecast_point.Rd b/man/as_forecast_point.Rd index 83ba83187..8e895ee73 100644 --- a/man/as_forecast_point.Rd +++ b/man/as_forecast_point.Rd @@ -14,6 +14,7 @@ as_forecast_point(data, ...) forecast_unit = NULL, observed = NULL, predicted = NULL, + verbose = TRUE, ... ) @@ -38,6 +39,9 @@ observed values. This column will be renamed to "observed".} \item{predicted}{(optional) Name of the column in \code{data} that contains the predicted values. This column will be renamed to "predicted".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_point} diff --git a/man/as_forecast_quantile.Rd b/man/as_forecast_quantile.Rd index 4cf407d0e..9704c5e03 100644 --- a/man/as_forecast_quantile.Rd +++ b/man/as_forecast_quantile.Rd @@ -15,6 +15,7 @@ as_forecast_quantile(data, ...) observed = NULL, predicted = NULL, quantile_level = NULL, + verbose = TRUE, ... ) @@ -49,6 +50,9 @@ predicted values. This column will be renamed to "predicted".} the quantile level of the predicted values. This column will be renamed to "quantile_level". Only applicable to quantile-based forecasts.} +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} + \item{probs}{A numeric vector of quantile levels for which quantiles will be computed. Corresponds to the \code{probs} argument in \code{\link[=quantile]{quantile()}}.} diff --git a/man/as_forecast_sample.Rd b/man/as_forecast_sample.Rd index bf179530c..3d38b7517 100644 --- a/man/as_forecast_sample.Rd +++ b/man/as_forecast_sample.Rd @@ -13,6 +13,7 @@ as_forecast_sample(data, ...) observed = NULL, predicted = NULL, sample_id = NULL, + verbose = TRUE, ... ) } @@ -38,6 +39,9 @@ predicted values. This column will be renamed to "predicted".} \item{sample_id}{(optional) Name of the column in \code{data} that contains the sample id. This column will be renamed to "sample_id".} + +\item{verbose}{Logical. If \code{FALSE} (default is \code{TRUE}), no messages and +warnings will be created.} } \value{ A \code{forecast} object of class \code{forecast_sample} diff --git a/tests/testthat/test-class-forecast-binary.R b/tests/testthat/test-class-forecast-binary.R index cb95e1d23..ff4b31083 100644 --- a/tests/testthat/test-class-forecast-binary.R +++ b/tests/testthat/test-class-forecast-binary.R @@ -7,6 +7,14 @@ test_that("output of as_forecast_binary() is accepted as input to score()", { expect_identical(score_check, suppressMessages(score(as_forecast_binary(example_binary)))) }) +test_that("as_forecast_binary() accepts verbose argument and suppresses messages", { + expect_no_condition( + as_forecast_binary(example_binary, verbose = FALSE) + ) + result <- as_forecast_binary(example_binary, verbose = FALSE) + expect_s3_class(result, "forecast_binary") +}) + # ============================================================================== # is_forecast_binary() # nolint: commented_code_linter diff --git a/tests/testthat/test-class-forecast-nominal.R b/tests/testthat/test-class-forecast-nominal.R index c73259e57..b898cdd7b 100644 --- a/tests/testthat/test-class-forecast-nominal.R +++ b/tests/testthat/test-class-forecast-nominal.R @@ -30,6 +30,14 @@ test_that("as_forecast.forecast_nominal() breaks when rows with zero probability ) }) +test_that("as_forecast_nominal() accepts verbose argument", { + expect_no_condition( + as_forecast_nominal(na.omit(example_nominal), verbose = FALSE) + ) + result <- as_forecast_nominal(na.omit(example_nominal), verbose = FALSE) + expect_s3_class(result, "forecast_nominal") +}) + # ============================================================================== # is_forecast_nominal() # nolint: commented_code_linter diff --git a/tests/testthat/test-class-forecast-point.R b/tests/testthat/test-class-forecast-point.R index fb2fd161d..a89aaf901 100644 --- a/tests/testthat/test-class-forecast-point.R +++ b/tests/testthat/test-class-forecast-point.R @@ -8,6 +8,14 @@ test_that("as_forecast_point() works", { ) }) +test_that("as_forecast_point() accepts verbose argument and suppresses messages", { + expect_no_condition( + as_forecast_point(example_point, verbose = FALSE) + ) + result <- as_forecast_point(example_point, verbose = FALSE) + expect_s3_class(result, "forecast_point") +}) + # ============================================================================== # is_forecast_point() # nolint: commented_code_linter diff --git a/tests/testthat/test-class-forecast-quantile.R b/tests/testthat/test-class-forecast-quantile.R index 4f46a5ed3..374916e99 100644 --- a/tests/testthat/test-class-forecast-quantile.R +++ b/tests/testthat/test-class-forecast-quantile.R @@ -196,6 +196,48 @@ test_that("as_forecast_quantile handles rounding issues correctly", { ) }) +test_that("as_forecast_quantile() accepts verbose argument and suppresses messages", { + expect_no_condition( + as_forecast_quantile(example_quantile, verbose = FALSE) + ) + result <- as_forecast_quantile(example_quantile, verbose = FALSE) + expect_s3_class(result, "forecast_quantile") +}) + +test_that("as_forecast_quantile() with verbose = TRUE emits messages by default", { + expect_message( + as_forecast_quantile(example_quantile), + "Some rows containing NA" + ) +}) + +test_that("as_forecast_quantile() verbose = FALSE suppresses quantile rounding warning", { + quantile_data <- data.table( + quantile_level = c(0.25, 0.75 + 1e-13, 0.25, 0.75), + predicted = c(1, 2, 3, 4), + observed = c(5, 5, 5, 5), + location = c(1, 1, 2, 2) + ) + expect_no_condition( + as_forecast_quantile(quantile_data, verbose = FALSE) + ) +}) + +test_that("as_forecast_quantile() verbose = FALSE does not affect error behavior", { + invalid_data <- data.table(observed = 1:5, predicted = 1:5) + expect_error( + as_forecast_quantile(invalid_data, verbose = FALSE), + "Column 'quantile_level' not found" + ) +}) + +test_that("as_forecast_quantile() verbose = FALSE suppresses different-number-of-quantiles warning", { + data <- na.omit(as.data.table(example_quantile))[-1000, ] + expect_no_condition( + as_forecast_quantile(data, verbose = FALSE) + ) +}) + diff --git a/tests/testthat/test-class-forecast-sample.R b/tests/testthat/test-class-forecast-sample.R index 995e49106..ee82cbf27 100644 --- a/tests/testthat/test-class-forecast-sample.R +++ b/tests/testthat/test-class-forecast-sample.R @@ -28,6 +28,15 @@ test_that("Running `as_forecast_sample()` twice returns the same object", { ) }) +test_that("as_forecast_sample() accepts verbose argument and suppresses messages", { + data <- data.table::copy(example_sample_continuous) + expect_no_condition( + as_forecast_sample(data, verbose = FALSE) + ) + result <- as_forecast_sample(data, verbose = FALSE) + expect_s3_class(result, "forecast_sample") +}) + # ============================================================================== # is_forecast_sample() # nolint: commented_code_linter