Title: | Run Code 'With' Temporarily Modified Global State |
---|---|
Description: | A set of functions to run code 'with' safely and temporarily modified global state. Many of these functions were originally a part of the 'devtools' package, this provides a simple package with limited dependencies to provide access to these functions. |
Authors: | Jim Hester [aut], Lionel Henry [aut, cre], Kirill Müller [aut], Kevin Ushey [aut], Hadley Wickham [aut], Winston Chang [aut], Jennifer Bryan [ctb], Richard Cotton [ctb], Posit Software, PBC [cph, fnd] |
Maintainer: | Lionel Henry <[email protected]> |
License: | MIT + file LICENSE |
Version: | 3.0.2.9000 |
Built: | 2024-10-28 15:15:53 UTC |
Source: | https://github.com/r-lib/withr |
Similar to on.exit()
, but allows one to attach
an expression to be evaluated when exiting any frame currently
on the stack. This provides a nice mechanism for scoping side
effects for the duration of a function's execution.
defer(expr, envir = parent.frame(), priority = c("first", "last")) defer_parent(expr, priority = c("first", "last")) deferred_run(envir = parent.frame()) deferred_clear(envir = parent.frame())
defer(expr, envir = parent.frame(), priority = c("first", "last")) defer_parent(expr, priority = c("first", "last")) deferred_run(envir = parent.frame()) deferred_clear(envir = parent.frame())
expr |
|
envir |
|
priority |
|
defer()
works by attaching handlers to the requested environment (as an
attribute called "handlers"
), and registering an exit handler that
executes the registered handler when the function associated with the
requested environment finishes execution.
Deferred events can be set on the global environment, primarily to facilitate
the interactive development of code that is intended to be executed inside a
function or test. A message alerts the user to the fact that an explicit
deferred_run()
is the only way to trigger these deferred events. Use
deferred_clear()
to clear them without evaluation. The global environment
scenario is the main motivation for these functions.
source()
withr handlers run within source()
are run when source()
exits
rather than line by line.
This is only the case when the script is sourced in globalenv()
.
For a local environment, the caller needs to set
options(withr.hook_source = TRUE)
. This is to avoid paying the
penalty of detecting source()
in the normal usage of defer()
.
# define a 'local' function that creates a file, and # removes it when the parent function has finished executing local_file <- function(path) { file.create(path) defer_parent(unlink(path)) } # create tempfile path path <- tempfile() # use 'local_file' in a function local({ local_file(path) stopifnot(file.exists(path)) }) # file is deleted as we leave 'local' local stopifnot(!file.exists(path)) # investigate how 'defer' modifies the # executing function's environment local({ local_file(path) print(attributes(environment())) }) # Note that examples lack function scoping so deferred calls are # generally executed immediately defer(print("one")) defer(print("two"))
# define a 'local' function that creates a file, and # removes it when the parent function has finished executing local_file <- function(path) { file.create(path) defer_parent(unlink(path)) } # create tempfile path path <- tempfile() # use 'local_file' in a function local({ local_file(path) stopifnot(file.exists(path)) }) # file is deleted as we leave 'local' local stopifnot(!file.exists(path)) # investigate how 'defer' modifies the # executing function's environment local({ local_file(path) print(attributes(environment())) }) # Note that examples lack function scoping so deferred calls are # generally executed immediately defer(print("one")) defer(print("two"))
Temporarily use a graphics device.
with_bmp(new, code, ...) local_bmp(new, ..., .local_envir = parent.frame()) with_cairo_pdf(new, code, ...) local_cairo_pdf(new, ..., .local_envir = parent.frame()) with_cairo_ps(new, code, ...) local_cairo_ps(new, ..., .local_envir = parent.frame()) with_pdf(new, code, ...) local_pdf(new, ..., .local_envir = parent.frame()) with_postscript(new, code, ...) local_postscript(new, ..., .local_envir = parent.frame()) with_svg(new, code, ...) local_svg(new, ..., .local_envir = parent.frame()) with_tiff(new, code, ...) local_tiff(new, ..., .local_envir = parent.frame()) with_xfig(new, code, ...) local_xfig(new, ..., .local_envir = parent.frame()) with_png(new, code, ...) local_png(new, ..., .local_envir = parent.frame()) with_jpeg(new, code, ...) local_jpeg(new, ..., .local_envir = parent.frame())
with_bmp(new, code, ...) local_bmp(new, ..., .local_envir = parent.frame()) with_cairo_pdf(new, code, ...) local_cairo_pdf(new, ..., .local_envir = parent.frame()) with_cairo_ps(new, code, ...) local_cairo_ps(new, ..., .local_envir = parent.frame()) with_pdf(new, code, ...) local_pdf(new, ..., .local_envir = parent.frame()) with_postscript(new, code, ...) local_postscript(new, ..., .local_envir = parent.frame()) with_svg(new, code, ...) local_svg(new, ..., .local_envir = parent.frame()) with_tiff(new, code, ...) local_tiff(new, ..., .local_envir = parent.frame()) with_xfig(new, code, ...) local_xfig(new, ..., .local_envir = parent.frame()) with_png(new, code, ...) local_png(new, ..., .local_envir = parent.frame()) with_jpeg(new, code, ...) local_jpeg(new, ..., .local_envir = parent.frame())
new |
|
code |
|
... |
Additional arguments passed to the graphics device. |
.local_envir |
|
with_bmp()
and local_bmp()
wrap around grDevices::bmp()
.
with_cairo_pdf()
and local_cairo_pdf()
wrap around grDevices::cairo_pdf()
.
with_cairo_ps()
and local_cairo_ps()
wrap around grDevices::cairo_ps()
.
with_pdf()
and local_pdf()
wrap around grDevices::pdf()
.
with_postscript()
and local_postscript()
wrap around grDevices::postscript()
.
with_svg()
and local_svg()
wrap around grDevices::svg()
.
with_tiff()
and local_tiff()
wrap around grDevices::tiff()
.
with_xfig()
and local_xfig()
wrap around grDevices::xfig()
.
with_png()
and local_png()
wrap around grDevices::png()
.
with_jpeg()
and local_jpeg()
wrap around grDevices::jpeg()
.
[any]
The results of the evaluation of the code
argument.
with_bmp()
: BMP device
with_cairo_pdf()
: CAIRO_PDF device
with_cairo_ps()
: CAIRO_PS device
with_pdf()
: PDF device
with_postscript()
: POSTSCRIPT device
with_svg()
: SVG device
with_tiff()
: TIFF device
with_xfig()
: XFIG device
with_png()
: PNG device
with_jpeg()
: JPEG device
withr
for examples
# dimensions are in inches with_pdf(file.path(tempdir(), "test.pdf"), width = 7, height = 5, plot(runif(5)) ) # dimensions are in pixels with_png(file.path(tempdir(), "test.png"), width = 800, height = 600, plot(runif(5)) )
# dimensions are in inches with_pdf(file.path(tempdir(), "test.pdf"), width = 7, height = 5, plot(runif(5)) ) # dimensions are in pixels with_png(file.path(tempdir(), "test.png"), width = 800, height = 600, plot(runif(5)) )
Temporarily change collation order by changing the value of the
LC_COLLATE
locale.
with_collate(new, code) local_collate(new = list(), .local_envir = parent.frame())
with_collate(new, code) local_collate(new = list(), .local_envir = parent.frame())
new |
|
code |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
# Modify collation order: x <- c("bernard", "bérénice", "béatrice", "boris") with_collate("fr_FR", sort(x)) #> [1] "béatrice" "bérénice" "bernard" "boris" with_collate("C", sort(x)) #> [1] "bernard" "boris" "béatrice" "bérénice"
withr
for examples
R file connections which are automatically closed.
with_connection(con, code) local_connection(con, .local_envir = parent.frame())
with_connection(con, code) local_connection(con, .local_envir = parent.frame())
con |
For |
code |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
with_connection(list(con = file("foo", "w")), { writeLines(c("foo", "bar"), con) }) read_foo <- function() { readLines(local_connection(file("foo", "r"))) } read_foo() unlink("foo")
with_connection(list(con = file("foo", "w")), { writeLines(c("foo", "bar"), con) }) read_foo <- function() { readLines(local_connection(file("foo", "r"))) } read_foo() unlink("foo")
Connections to Database Management Systems which automatically disconnect. In
particular connections which are created with DBI::dbConnect()
and closed
with DBI::dbDisconnect()
.
with_db_connection(con, code) local_db_connection(con, .local_envir = parent.frame())
with_db_connection(con, code) local_db_connection(con, .local_envir = parent.frame())
con |
For |
code |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
db <- tempfile() with_db_connection( list(con = DBI::dbConnect(RSQLite::SQLite(), db)), { DBI::dbWriteTable(con, "mtcars", mtcars) }) head_db_table <- function(...) { con <- local_db_connection(DBI::dbConnect(RSQLite::SQLite(), db)) head(DBI::dbReadTable(con, "mtcars"), ...) } head_db_table() unlink(db)
db <- tempfile() with_db_connection( list(con = DBI::dbConnect(RSQLite::SQLite(), db)), { DBI::dbWriteTable(con, "mtcars", mtcars) }) head_db_table <- function(...) { con <- local_db_connection(DBI::dbConnect(RSQLite::SQLite(), db)) head(DBI::dbReadTable(con, "mtcars"), ...) } head_db_table() unlink(db)
Temporarily change the current working directory.
with_dir(new, code) local_dir(new = list(), .local_envir = parent.frame())
with_dir(new, code) local_dir(new = list(), .local_envir = parent.frame())
new |
|
code |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
getwd() with_dir(tempdir(), getwd())
getwd() with_dir(tempdir(), getwd())
Temporarily change system environment variables.
with_envvar(new, code, action = "replace") local_envvar( .new = list(), ..., action = "replace", .local_envir = parent.frame() )
with_envvar(new, code, action = "replace") local_envvar( .new = list(), ..., action = "replace", .local_envir = parent.frame() )
new , .new
|
|
code |
|
action |
should new values |
... |
Named arguments with new environment variables. |
.local_envir |
|
if NA
is used those environment variables will be unset.
If there are any duplicated variable names only the last one is used.
[any]
The results of the evaluation of the code
argument.
withr
for examples
with_envvar(new = c("GITHUB_PAT" = "abcdef"), Sys.getenv("GITHUB_PAT")) # with_envvar unsets variables after usage Sys.getenv("TEMP_SECRET") with_envvar(new = c("TEMP_SECRET" = "secret"), Sys.getenv("TEMP_SECRET")) Sys.getenv("TEMP_SECRET")
with_envvar(new = c("GITHUB_PAT" = "abcdef"), Sys.getenv("GITHUB_PAT")) # with_envvar unsets variables after usage Sys.getenv("TEMP_SECRET") with_envvar(new = c("TEMP_SECRET" = "secret"), Sys.getenv("TEMP_SECRET")) Sys.getenv("TEMP_SECRET")
Create files, which are then automatically removed afterwards.
with_file(file, code) local_file(.file, ..., .local_envir = parent.frame())
with_file(file, code) local_file(.file, ..., .local_envir = parent.frame())
file , .file
|
|
code |
|
... |
Additional (possibly named) arguments of files to create. |
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
with_file("file1", { writeLines("foo", "file1") readLines("file1") }) with_file(list("file1" = writeLines("foo", "file1")), { readLines("file1") })
with_file("file1", { writeLines("foo", "file1") readLines("file1") }) with_file(list("file1" = writeLines("foo", "file1")), { readLines("file1") })
Temporarily turn gctorture2 on.
with_gctorture2(new, code, wait = new, inhibit_release = FALSE)
with_gctorture2(new, code, wait = new, inhibit_release = FALSE)
new |
|
code |
|
wait |
integer; number of allocations to wait before starting GC torture. |
inhibit_release |
logical; do not release free objects for re-use: use with caution. |
[any]
The results of the evaluation of the code
argument.
withr
for examples
Temporarily change the language used for translations.
with_language(lang, code) local_language(lang, .local_envir = parent.frame())
with_language(lang, code) local_language(lang, .local_envir = parent.frame())
lang |
A BCP47 language code like "en" (English), "fr" (French), "fr_CA" (French Canadian). Formally, this is a lower case two letter ISO 639 country code, optionally followed by "_" or "-" and an upper case two letter ISO 3166 region code. |
code |
|
.local_envir |
|
with_language("en", try(mean[[1]])) with_language("fr", try(mean[[1]])) with_language("es", try(mean[[1]]))
with_language("en", try(mean[[1]])) with_language("fr", try(mean[[1]])) with_language("es", try(mean[[1]]))
Temporarily change library paths.
with_libpaths(new, code, action = "replace") local_libpaths(new = list(), action = "replace", .local_envir = parent.frame())
with_libpaths(new, code, action = "replace") local_libpaths(new = list(), action = "replace", .local_envir = parent.frame())
new |
|
code |
|
action |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
Other libpaths:
with_temp_libpaths()
.libPaths() new_lib <- tempfile() dir.create(new_lib) with_libpaths(new_lib, print(.libPaths())) unlink(new_lib, recursive = TRUE)
.libPaths() new_lib <- tempfile() dir.create(new_lib) with_libpaths(new_lib, print(.libPaths())) unlink(new_lib, recursive = TRUE)
Temporarily change locale settings.
with_locale(new, code) local_locale(.new = list(), ..., .local_envir = parent.frame())
with_locale(new, code) local_locale(.new = list(), ..., .local_envir = parent.frame())
new , .new
|
|
code |
|
... |
Additional arguments with locale settings. |
.local_envir |
|
Setting the LC_ALL
category is currently not implemented.
[any]
The results of the evaluation of the code
argument.
withr
for examples
## Change locale for time: df <- data.frame( stringsAsFactors = FALSE, date = as.Date(c("2019-01-01", "2019-02-01")), value = c(1, 2) ) with_locale(new = c("LC_TIME" = "es_ES"), code = plot(df$date, df$value)) ## Compare with: # plot(df$date, df$value) ## Month names: with_locale(new = c("LC_TIME" = "en_GB"), format(ISOdate(2000, 1:12, 1), "%B")) with_locale(new = c("LC_TIME" = "es_ES"), format(ISOdate(2000, 1:12, 1), "%B")) ## Change locale for currencies: with_locale(new = c("LC_MONETARY" = "it_IT"), Sys.localeconv()) with_locale(new = c("LC_MONETARY" = "en_US"), Sys.localeconv()) ## Ordering: x <- c("bernard", "bérénice", "béatrice", "boris") with_locale(c(LC_COLLATE = "fr_FR"), sort(x)) with_locale(c(LC_COLLATE = "C"), sort(x))
## Change locale for time: df <- data.frame( stringsAsFactors = FALSE, date = as.Date(c("2019-01-01", "2019-02-01")), value = c(1, 2) ) with_locale(new = c("LC_TIME" = "es_ES"), code = plot(df$date, df$value)) ## Compare with: # plot(df$date, df$value) ## Month names: with_locale(new = c("LC_TIME" = "en_GB"), format(ISOdate(2000, 1:12, 1), "%B")) with_locale(new = c("LC_TIME" = "es_ES"), format(ISOdate(2000, 1:12, 1), "%B")) ## Change locale for currencies: with_locale(new = c("LC_MONETARY" = "it_IT"), Sys.localeconv()) with_locale(new = c("LC_MONETARY" = "en_US"), Sys.localeconv()) ## Ordering: x <- c("bernard", "bérénice", "béatrice", "boris") with_locale(c(LC_COLLATE = "fr_FR"), sort(x)) with_locale(c(LC_COLLATE = "C"), sort(x))
Temporarily change contents of an existing Makevars
file.
with_makevars( new, code, path = makevars_user(), assignment = c("=", ":=", "?=", "+=") ) local_makevars( .new = list(), ..., .path = makevars_user(), .assignment = c("=", ":=", "?=", "+="), .local_envir = parent.frame() )
with_makevars( new, code, path = makevars_user(), assignment = c("=", ":=", "?=", "+=") ) local_makevars( .new = list(), ..., .path = makevars_user(), .assignment = c("=", ":=", "?=", "+="), .local_envir = parent.frame() )
new , .new
|
|
code |
|
path , .path
|
|
assignment , .assignment
|
|
... |
Additional new variables and their values. |
.local_envir |
|
If no Makevars
file exists or the fields in new
do
not exist in the existing Makevars
file then the fields are added to
the new file. Existing fields which are not included in new
are
appended unchanged. Fields which exist in Makevars
and in new
are modified to use the value in new
.
[any]
The results of the evaluation of the code
argument.
withr
for examples
writeLines("void foo(int* bar) { *bar = 1; }\n", "foo.c") system("R CMD SHLIB --preclean -c foo.c") with_makevars(c(CFLAGS = "-O3"), system("R CMD SHLIB --preclean -c foo.c")) unlink(c("foo.c", "foo.so"))
writeLines("void foo(int* bar) { *bar = 1; }\n", "foo.c") system("R CMD SHLIB --preclean -c foo.c") with_makevars(c(CFLAGS = "-O3"), system("R CMD SHLIB --preclean -c foo.c")) unlink(c("foo.c", "foo.so"))
Temporarily change global options.
with_options(new, code) local_options(.new = list(), ..., .local_envir = parent.frame())
with_options(new, code) local_options(.new = list(), ..., .local_envir = parent.frame())
new , .new
|
|
code |
|
... |
Additional options and their values |
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
# number of significant digits to print getOption("digits") # modify temporarily the number of significant digits to print with_options(list(digits = 3), getOption("digits")) with_options(list(digits = 3), print(pi)) # modify temporarily the character to be used as the decimal point getOption("digits") with_options(list(OutDec = ","), print(pi)) # modify temporarily multiple options with_options(list(OutDec = ",", digits = 3), print(pi)) # modify, within the scope of the function, the number of # significant digits to print print_3_digits <- function(x) { # assign 3 to the option "digits" for the rest of this function # after the function exits, the option will return to its previous # value local_options(list(digits = 3)) print(x) } print_3_digits(pi) # returns 3.14 print(pi) # returns 3.141593
# number of significant digits to print getOption("digits") # modify temporarily the number of significant digits to print with_options(list(digits = 3), getOption("digits")) with_options(list(digits = 3), print(pi)) # modify temporarily the character to be used as the decimal point getOption("digits") with_options(list(OutDec = ","), print(pi)) # modify temporarily multiple options with_options(list(OutDec = ",", digits = 3), print(pi)) # modify, within the scope of the function, the number of # significant digits to print print_3_digits <- function(x) { # assign 3 to the option "digits" for the rest of this function # after the function exits, the option will return to its previous # value local_options(list(digits = 3)) print(x) } print_3_digits(pi) # returns 3.14 print(pi) # returns 3.141593
with_package()
attaches a package to the search path, executes the code, then
removes the package from the search path. The package namespace is not
unloaded however. with_namespace()
does the same thing, but attaches the
package namespace to the search path, so all objects (even unexported ones) are also
available on the search path.
with_package( package, code, pos = 2, lib.loc = NULL, character.only = TRUE, logical.return = FALSE, warn.conflicts = FALSE, quietly = TRUE, verbose = getOption("verbose") ) local_package( package, pos = 2, lib.loc = NULL, character.only = TRUE, logical.return = FALSE, warn.conflicts = FALSE, quietly = TRUE, verbose = getOption("verbose"), .local_envir = parent.frame() ) with_namespace(package, code, warn.conflicts = FALSE) local_namespace(package, .local_envir = parent.frame(), warn.conflicts = FALSE) with_environment( env, code, pos = 2L, name = format(env), warn.conflicts = FALSE ) local_environment( env, pos = 2L, name = format(env), warn.conflicts = FALSE, .local_envir = parent.frame() )
with_package( package, code, pos = 2, lib.loc = NULL, character.only = TRUE, logical.return = FALSE, warn.conflicts = FALSE, quietly = TRUE, verbose = getOption("verbose") ) local_package( package, pos = 2, lib.loc = NULL, character.only = TRUE, logical.return = FALSE, warn.conflicts = FALSE, quietly = TRUE, verbose = getOption("verbose"), .local_envir = parent.frame() ) with_namespace(package, code, warn.conflicts = FALSE) local_namespace(package, .local_envir = parent.frame(), warn.conflicts = FALSE) with_environment( env, code, pos = 2L, name = format(env), warn.conflicts = FALSE ) local_environment( env, pos = 2L, name = format(env), warn.conflicts = FALSE, .local_envir = parent.frame() )
package |
|
code |
|
pos |
the position on the search list at which to attach the
loaded namespace. Can also be the name of a position on the current
search list as given by |
lib.loc |
a character vector describing the location of R
library trees to search through, or |
character.only |
a logical indicating whether |
logical.return |
logical. If it is |
warn.conflicts |
logical. If |
quietly |
a logical. If |
verbose |
a logical. If |
.local_envir |
|
env |
|
name |
name to use for the attached database. Names starting with
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
## Not run: with_package("ggplot2", { ggplot(mtcars) + geom_point(aes(wt, hp)) }) ## End(Not run)
## Not run: with_package("ggplot2", { ggplot(mtcars) + geom_point(aes(wt, hp)) }) ## End(Not run)
Temporarily change graphics parameters.
with_par(new, code, no.readonly = FALSE) local_par( .new = list(), ..., no.readonly = FALSE, .local_envir = parent.frame() )
with_par(new, code, no.readonly = FALSE) local_par( .new = list(), ..., no.readonly = FALSE, .local_envir = parent.frame() )
new , .new
|
|
code |
|
no.readonly |
|
... |
Additional graphics parameters and their values. |
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
old <- par("col" = "black") # This will be in red with_par(list(col = "red", pch = 19), plot(mtcars$hp, mtcars$wt) ) # This will still be in black plot(mtcars$hp, mtcars$wt) par(old)
old <- par("col" = "black") # This will be in red with_par(list(col = "red", pch = 19), plot(mtcars$hp, mtcars$wt) ) # This will still be in black plot(mtcars$hp, mtcars$wt) par(old)
Temporarily change the system search path.
with_path(new, code, action = c("prefix", "suffix", "replace")) local_path( new = list(), action = c("prefix", "suffix", "replace"), .local_envir = parent.frame() )
with_path(new, code, action = c("prefix", "suffix", "replace")) local_path( new = list(), action = c("prefix", "suffix", "replace"), .local_envir = parent.frame() )
new |
|
code |
|
action |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
# temporarily modify the system PATH, *prefixing* the current path with_path(getwd(), Sys.getenv("PATH")) # temporarily modify the system PATH, *appending* to the current path with_path(getwd(), Sys.getenv("PATH"), "suffix")
# temporarily modify the system PATH, *prefixing* the current path with_path(getwd(), Sys.getenv("PATH")) # temporarily modify the system PATH, *appending* to the current path with_path(getwd(), Sys.getenv("PATH"), "suffix")
Change the RNG version and restore it afterwards.
with_rng_version(version, code) local_rng_version(version, .local_envir = parent.frame())
with_rng_version(version, code) local_rng_version(version, .local_envir = parent.frame())
version |
|
code |
|
.local_envir |
The environment to apply the change to. |
with_rng_version()
runs the code with the specified RNG version and
resets it afterwards.
local_rng_version()
changes the RNG version for the caller
execution environment.
[any]
The results of the evaluation of the code
argument.
withr
for examples
RNGversion()
, RNGkind()
, with_seed()
.
RNGkind() with_rng_version("3.0.0", RNGkind()) with_rng_version("1.6.0", RNGkind()) with_rng_version("3.0.0", with_seed(42, sample(1:100, 3))) with_rng_version("1.6.0", with_seed(42, sample(1:100, 3))) RNGkind() fun1 <- function() { local_rng_version("3.0.0") with_seed(42, sample(1:100, 3)) } fun2 <- function() { local_rng_version("1.6.0") with_seed(42, sample(1:100, 3)) } RNGkind() fun1() fun2() RNGkind()
RNGkind() with_rng_version("3.0.0", RNGkind()) with_rng_version("1.6.0", RNGkind()) with_rng_version("3.0.0", with_seed(42, sample(1:100, 3))) with_rng_version("1.6.0", with_seed(42, sample(1:100, 3))) RNGkind() fun1 <- function() { local_rng_version("3.0.0") with_seed(42, sample(1:100, 3)) } fun2 <- function() { local_rng_version("1.6.0") with_seed(42, sample(1:100, 3)) } RNGkind() fun1() fun2() RNGkind()
with_seed()
runs code with a specific random seed and resets it afterwards.
with_preserve_seed()
runs code with the current random seed and resets it
afterwards.
with_seed( seed, code, .rng_kind = NULL, .rng_normal_kind = NULL, .rng_sample_kind = NULL ) local_seed( seed, .local_envir = parent.frame(), .rng_kind = NULL, .rng_normal_kind = NULL, .rng_sample_kind = NULL ) with_preserve_seed(code) local_preserve_seed(.local_envir = parent.frame())
with_seed( seed, code, .rng_kind = NULL, .rng_normal_kind = NULL, .rng_sample_kind = NULL ) local_seed( seed, .local_envir = parent.frame(), .rng_kind = NULL, .rng_normal_kind = NULL, .rng_sample_kind = NULL ) with_preserve_seed(code) local_preserve_seed(.local_envir = parent.frame())
seed |
|
code |
|
.rng_kind , .rng_normal_kind , .rng_sample_kind
|
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
# Same random values: with_preserve_seed(runif(5)) with_preserve_seed(runif(5)) # Use a pseudorandom value as seed to advance the RNG and pick a different # value for the next call: with_seed(seed <- sample.int(.Machine$integer.max, 1L), runif(5)) with_seed(seed, runif(5)) with_seed(seed <- sample.int(.Machine$integer.max, 1L), runif(5))
# Same random values: with_preserve_seed(runif(5)) with_preserve_seed(runif(5)) # Use a pseudorandom value as seed to advance the RNG and pick a different # value for the next call: with_seed(seed <- sample.int(.Machine$integer.max, 1L), runif(5)) with_seed(seed, runif(5)) with_seed(seed <- sample.int(.Machine$integer.max, 1L), runif(5))
Temporarily divert output to a file via sink()
. For
sinks of type message
, an error is raised if such a sink is already
active.
with_output_sink(new, code, append = FALSE, split = FALSE) local_output_sink( new = list(), append = FALSE, split = FALSE, .local_envir = parent.frame() ) with_message_sink(new, code, append = FALSE) local_message_sink(new = list(), append = FALSE, .local_envir = parent.frame())
with_output_sink(new, code, append = FALSE, split = FALSE) local_output_sink( new = list(), append = FALSE, split = FALSE, .local_envir = parent.frame() ) with_message_sink(new, code, append = FALSE) local_message_sink(new = list(), append = FALSE, .local_envir = parent.frame())
new |
|
code |
|
append |
logical. If |
split |
logical: if |
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
Temporarily prepend a new temporary directory to the library paths.
with_temp_libpaths(code, action = "prefix") local_temp_libpaths(action = "prefix", .local_envir = parent.frame())
with_temp_libpaths(code, action = "prefix") local_temp_libpaths(action = "prefix", .local_envir = parent.frame())
code |
|
action |
|
.local_envir |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
Other libpaths:
with_libpaths()
Temporarily create a file or directory, which will automatically deleted once you're finished with it.
with_tempfile( new, code, envir = parent.frame(), .local_envir = parent.frame(), pattern = "file", tmpdir = tempdir(), fileext = "" ) local_tempfile( new = NULL, lines = NULL, envir = parent.frame(), .local_envir = parent.frame(), pattern = "file", tmpdir = tempdir(), fileext = "" ) with_tempdir( code, clean = TRUE, pattern = "file", tmpdir = tempdir(), fileext = "" ) local_tempdir( pattern = "file", tmpdir = tempdir(), fileext = "", .local_envir = parent.frame(), clean = TRUE )
with_tempfile( new, code, envir = parent.frame(), .local_envir = parent.frame(), pattern = "file", tmpdir = tempdir(), fileext = "" ) local_tempfile( new = NULL, lines = NULL, envir = parent.frame(), .local_envir = parent.frame(), pattern = "file", tmpdir = tempdir(), fileext = "" ) with_tempdir( code, clean = TRUE, pattern = "file", tmpdir = tempdir(), fileext = "" ) local_tempdir( pattern = "file", tmpdir = tempdir(), fileext = "", .local_envir = parent.frame(), clean = TRUE )
new |
|
code |
|
envir |
|
.local_envir |
|
pattern |
a non-empty character vector giving the initial part of the name. |
tmpdir |
a non-empty character vector giving the directory name. |
fileext |
a non-empty character vector giving the file extension. |
lines |
Optionally, supply a character vector of lines to be written to
|
clean |
|
[any]
The results of the evaluation of the code
argument.
withr
for examples
# local_tempfile() is the easiest to use because it returns a path local({ path1 <<- local_tempfile(lines = c("x,y", "1,2")) readLines(path1) }) # the file is deleted automatically file.exists(path1) # with_tempfile() is a bit trickier; the first argument gives the name # of a variable that will contain the path: with_tempfile("path2", { print(path2) write.csv(iris, path2) file.size(path2) }) # Note that this variable is only available in the scope of with_tempfile try(path2)
# local_tempfile() is the easiest to use because it returns a path local({ path1 <<- local_tempfile(lines = c("x,y", "1,2")) readLines(path1) }) # the file is deleted automatically file.exists(path1) # with_tempfile() is a bit trickier; the first argument gives the name # of a variable that will contain the path: with_tempfile("path2", { print(path2) write.csv(iris, path2) file.size(path2) }) # Note that this variable is only available in the scope of with_tempfile try(path2)
Change the time zone, and restore it afterwards.
with_timezone(tz, code) local_timezone(tz, .local_envir = parent.frame())
with_timezone(tz, code) local_timezone(tz, .local_envir = parent.frame())
tz |
|
code |
|
.local_envir |
The environment to apply the change to. |
with_timezone()
runs the code with the specified time zone and
resets it afterwards.
local_timezone()
changes the time zone for the caller
execution environment.
[any]
The results of the evaluation of the code
argument.
withr
for examples
Sys.time() with_timezone("Europe/Paris", print(Sys.time())) with_timezone("America/Los_Angeles", print(Sys.time())) fun1 <- function() { local_timezone("CET") print(Sys.time()) } fun2 <- function() { local_timezone("America/Los_Angeles") print(Sys.time()) } Sys.time() fun1() fun2() Sys.time()
Sys.time() with_timezone("Europe/Paris", print(Sys.time())) with_timezone("America/Los_Angeles", print(Sys.time())) fun1 <- function() { local_timezone("CET") print(Sys.time()) } fun2 <- function() { local_timezone("America/Los_Angeles") print(Sys.time()) } Sys.time() fun1() fun2() Sys.time()
All functions prefixed by with_
work as follows. First, a particular
aspect of the global environment is modified (see below for a list).
Then, custom code (passed via the code
argument) is executed.
Upon completion or error, the global environment is restored to the previous
state. Each with_
function has a local_
variant, which instead resets
the state when the current evaluation context ends (such as the end of a
function).
new |
[various] |
Values for setting |
code |
[any] |
Code to execute in the temporary environment |
... |
Further arguments | |
with_...(new, code, ...)
with_collate()
: collation order
with_dir()
: working directory
with_envvar()
: environment variables
with_libpaths()
: library paths, replacing current libpaths
with_locale()
: any locale setting
with_makevars()
: Makevars variables
with_options()
: options
with_par()
: graphics parameters
with_path()
: PATH
environment variable
with_sink()
: output redirection
All with_
functions are created by a helper function,
with_()
. This functions accepts two arguments:
a setter function and an optional resetter function. The setter function is
expected to change the global state and return an "undo instruction".
This undo instruction is then passed to the resetter function, which changes
back the global state. In many cases, the setter function can be used
naturally as resetter.
Maintainer: Lionel Henry [email protected]
Authors:
Jim Hester
Kirill Müller [email protected]
Kevin Ushey [email protected]
Hadley Wickham [email protected]
Winston Chang
Other contributors:
Jennifer Bryan [contributor]
Richard Cotton [contributor]
Posit Software, PBC [copyright holder, funder]
Useful links:
Report bugs at https://github.com/r-lib/withr/issues
getwd() with_dir(tempdir(), getwd()) getwd() Sys.getenv("WITHR") with_envvar(c("WITHR" = 2), Sys.getenv("WITHR")) Sys.getenv("WITHR") with_envvar(c("A" = 1), with_envvar(c("A" = 2), action = "suffix", Sys.getenv("A")) ) # local variants are best used within other functions f <- function(x) { local_envvar(c("WITHR" = 2)) Sys.getenv("WITHR") } Sys.getenv("WITHR")
getwd() with_dir(tempdir(), getwd()) getwd() Sys.getenv("WITHR") with_envvar(c("WITHR" = 2), Sys.getenv("WITHR")) Sys.getenv("WITHR") with_envvar(c("A" = 1), with_envvar(c("A" = 2), action = "suffix", Sys.getenv("A")) ) # local variants are best used within other functions f <- function(x) { local_envvar(c("WITHR" = 2)) Sys.getenv("WITHR") } Sys.getenv("WITHR")