-
Notifications
You must be signed in to change notification settings - Fork 11
Expand file tree
/
Copy pathlambda.R
More file actions
121 lines (111 loc) · 2.83 KB
/
lambda.R
File metadata and controls
121 lines (111 loc) · 2.83 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
#' Build an anonymous function.
#'
#'
#' @param params formal parameters of function, unbound names.
#' @param body substituted body of function to map arguments into.
#' @param env environment to work in.
#' @return user defined function.
#'
#' @seealso \code{\link{lambda}}, \code{\link{defineLambda}}, \code{\link{named_map_builder}}
#'
#' @examples
#'
#' f <- makeFunction_se(as.name('x'), substitute({x*x}))
#' f(7)
#'
#'
#' g <- makeFunction_se(c(as.name('x'), as.name('y')), substitute({ x + 3*y }))
#' g(1,100)
#'
#'
#' @export
#'
makeFunction_se <- function(params, body, env = parent.frame()) {
force(env)
vars <- as.character(params)
formals <- replicate(length(vars), quote(expr = ))
names(formals) <- vars
eval(call('function', as.pairlist(formals), body),
envir = env,
enclos = env)
}
#' Build an anonymous function of dot.
#'
#' @param body function body
#' @param env environment to work in.
#' @return user defined function.
#'
#' @seealso \code{\link{lambda}}, \code{\link{defineLambda}}, \code{\link{named_map_builder}}, \code{\link{makeFunction_se}}
#'
#' @examples
#'
#' f <- f.(sin(.) %.>% cos(.))
#' 7 %.>% f
#'
#'
#' @export
#'
f. <- function(body, env = parent.frame()) {
force(env)
body <- substitute(body)
wrapr::makeFunction_se('.', body, env)
}
#' Build an anonymous function.
#'
#' Mostly just a place-holder so lambda-symbol form has somewhere safe to hang its help entry.
#'
#' @param ... formal parameters of function, unbound names, followed by function body (code/language).
#' @param env environment to work in
#' @return user defined function.
#'
#'
#' @seealso \code{\link{defineLambda}}, \code{\link{makeFunction_se}}, \code{\link{named_map_builder}}
#'
#' @examples
#'
#' #lambda-syntax: lambda(arg [, arg]*, body [, env=env])
#' # also works with lambda character as function name
#' # print(intToUtf8(0x03BB))
#'
#' # example: square numbers
#' sapply(1:4, lambda(x, x^2))
#'
#' # example more than one argument
#' f <- lambda(x, y, x+y)
#' f(2,4)
#'
#'
#' @export
#'
lambda <- function(..., env = parent.frame()) {
force(env)
args <- base::substitute(list(...))
body <- args[[length(args)]]
args <- args[-length(args)]
params <- base::lapply(args[-1], base::as.name)
wrapr::makeFunction_se(params, body, env)
}
#' Define lambda function building function.
#'
#' Use this to place a copy of the lambda-symbol
#' function builder in your workspace.
#'
#' @param envir environment to work in.
#' @param name character, name to assign to (defaults to Greek lambda).
#'
#' @seealso \code{\link{lambda}}, \code{\link{makeFunction_se}}, \code{\link{named_map_builder}}
#'
#' @examples
#'
#' defineLambda()
#' # ls()
#'
#' @export
#'
defineLambda <- function(envir = parent.frame(), name = NULL) {
force(envir)
if(is.null(name)) {
name <- intToUtf8(0x03BB)
}
assign(name, wrapr::lambda, envir = envir)
}