Here's another way:
makeSolver <- function() {
f1 <- function(x, K) K - x
f2 <- function(x, r, K) r * x * f1(x, K)
function() f1(3,4) + f2(1,2,3)
}
solverB <- makeSolver()
solverB()
makeSolver (implicitly) creates an environment, installs f1 and f2
into it, and then returns a function that gets assigned to
solverB. Calling solverB invokes the function in makeSolver, so f1
and f2 are visible to it. The principle is similar to the 'bank
account' example in section 10.7 of 'An introduction to R',
available
in the manuals section of cran.
A down side is that the signature of solverB is not obvious; I'm not
sure how the documentation facilities (R CMD check) cope with this.
Nice poster at useR!
Martin
Thomas Petzoldt <thpe at hhbio.wasser.tu-dresden.de> writes:
> Hello,
>
> I discussed the following problem on the great useR conference with
> several people and wonder if someone of you knows a more elegant (or
> more common ?) solution than the one below.
>
> The problem:
> ===========>
> I have several sets of interrelated functions which should be compared.
> The functions themselves have different structure, application-specific
> names (for readability) and they should be exchangeable. I want to avoid
> to construct a generic for every new function, but the functions should
> be aggregated together in a common data structure (e.g. list "eq"
or an
> S4 instance) *and* it should be able for them to "see" and call
each
> other with too many $ or @. These functions are used in another function
> (called "solver" here) which may be used to prepare something
before the
> call to f2.
>
> The example and a possible solution (which uses an environment
> manipulating function "putInEnv()") is given below.
>
> Thanks a lot
>
> Thomas
>
>
> ##=====================================================> ## An example
> ##=====================================================>
> ## a small list of functions
> eq <- list(
> f1 = function(x, K) K - x,
> f2 = function(x, r, K) r * x * f1(x, K)
> )
>
> ## a solver fnction which calls them
> solverB <- function(eq) {
> eq <- putInEnv(eq, environment()) # that's the trick
> f1(3,4) + f2(1,2,3)
> }
>
> ## and the final call (e.g. from the command line)
> solverB(eq)
>
>
> ##=====================================================> ## One possible
solution. Is there a better one???
> ##=====================================================>
>
> putInEnv <- function(eq, e) {
> ## clone, very important to avoid "interferences"!!!
> eq <- as.list(unlist(eq))
> lapply(eq, "environment<-", e)
> nn <- names(eq)
> for (i in 1:length(eq)) {
> assign(nn[i], eq[[i]], envir = e)
> }
> eq
> }
>
> ______________________________________________
> R-help at stat.math.ethz.ch mailing list
> https://stat.ethz.ch/mailman/listinfo/r-help
> PLEASE do read the posting guide!
http://www.R-project.org/posting-guide.html