Section a functions domain by fixing certain arguments of a function call.

set_default(fun, nms, vls = NULL)

section_fun(fun, nms, vls = NULL, method = "args")

section_fun_sub(fun, nms, vls = NULL, envir = parent.frame())

section_fun_env(fun, nms, vls = NULL)

get_section(object)

get_fun(object)

Arguments

fun

Function to be sectioned

nms

Either a named list of the form name=value where each name is the name of an argument of the function (in which case vls is ignored) or a character vector of names of arguments.

vls

A vector or list of values of the arguments

method

One of the following: 1) "args" (default); based on substituting fixed values into the function argument list as default values). For backward compatibility can also be "def". 2) "body" for substituting fixed values into the function body. For backward compatibility can also be "sub". 3) "env": (for environment); using an auxillary argument for storing sectioned values.

envir

Environment

object

An object from section_fun (a scaffold object).

Value

A new function: The input function fun but with certain arguments fixed at specific values.

Details

Let E be a subset of the cartesian product X x Y where X and Y are some sets. Consider a function f(x,y) defined on E. Then for any x in X, the section of E defined by x (denoted Ex) is the set of $y$s in Y such that (x, y) is in E. Correspondingly, the section of f(x,y) defined by x is the function $f_x$ defined on Ex given by $f_x(y)=f(x,y)$.

section_fun is a wrapper for calling set_default (default method), section_fun_env or section_fun_sub. Notice that creating a sectioned function with section_fun_sub can be time consuming.

Author

Søren Højsgaard, sorenh@math.aau.dk based on code adapted from the curry package.

Examples


f  <- function(x, y){x + y}

f_ <- section_fun(f, list(y = 10),    method="args") ## "def"" is default
f_ <- section_fun(f, nms="y", vls=10, method="args") ## SAME AS ABOVE
f_
#> function (x, y = 10) 
#> {
#>     x + y
#> }
#> <environment: 0x56d101aacdb8>
f_(x=1)
#> [1] 11

f_ <- section_fun(f, list(y = 10),    method="body") ## 
f_ <- section_fun(f, nms="y", vls=10, method="body") ## SAME AS ABOVE
f_
#> function (x) 
#> {
#>     y = 10
#>     x + y
#> }
#> <environment: 0x56d101aacdb8>
f_(x=1)
#> [1] 11

f_ <- section_fun(f, list(y = 10),    method="env")
f_ <- section_fun(f, nms="y", vls=10, method="env") ## SAME AS ABOVE
f_
#> function (x) 
#> {
#>     . <- "use get_section(function_name) to see section"
#>     . <- "use get_fun(function_name) to see original function"
#>     args <- arg_getter()
#>     do.call(fun, args)
#> }
#> <environment: 0x56d0fea9e598>
f_(x=1)
#> [1] 11
get_section(f_)
#> $y
#> [1] 10
#> 
get_fun(f_)
#> function(x, y){x + y}
#> <environment: 0x56d101aacdb8>

 
## With more complicated values:
g <- function(A, B) {
  A + B
}
g_ <- section_fun(g, list(A = matrix(1:4, nrow=2)))
g_ <- section_fun(g, "A", list(matrix(1:4, nrow=2)))
g_(diag(1, 2))
#>      [,1] [,2]
#> [1,]    2    3
#> [2,]    2    5

g_ <- section_fun(g, list(A = matrix(1:4, nrow=2)))

## Using built in function
set.seed(123)
rnorm5 <- section_fun(rnorm, list(n=5)) 
rnorm5(0, 1)
#> [1] -0.56047565 -0.23017749  1.55870831  0.07050839  0.12928774

set.seed(123)
rnorm(5)
#> [1] -0.56047565 -0.23017749  1.55870831  0.07050839  0.12928774