On 05/04/2012 4:20 PM, John C Nash wrote:
In trying to streamline various optimization functions, I would like to have a
scratch pad
of working data that is shared across a number of functions. These can be
called from
different levels within some wrapper functions for maximum likelihood and other
such
computations. I'm sure there are other applications that could benefit from
this.
Below are two approaches. One uses the<<- assignment to a structure I call
OPCON. The
other attempts to create an environment with this name, but fails. Though I
have looked at
a number of references, I have so far not found an adequate description of how
to specify
where the OPCON environment is located. (Both the green and blue books do not
cover this
topic, at least not under "environment" in the index.)
Is there a recommended approach to this?
The one I would use is to create all of the functions that need access
to the scratch pad as local functions within another. For example,
makethem <- function() {
MAXIMIZE <- TRUE
PARSCALE <- rep(1, npar)
KFN <- 0
... etc ...
add1 <- function(){
KFN <<- 1 + KFN
}
list(add1 = add1, ... other functions here...)
}
A single call to makethem() will return a list of functions which all
have access to MAXIMIZE, PARSCALE, etc. If you like, you can pull them
out of the list to be called independently, e.g.
fns <- makethem()
add1 <- fns$add1
and they'll still have access. (If this is a one-off need, you can use
local( ) around the definitions, but I prefer the wrapper-function style.
I realize I could use argument lists, but they
get long and tedious with the number of items I may need to pass, though
passing the OPCON
structure in and out might be the proper way. An onAttach() approach was
suggested by Paul
Gilbert and tried, but it has so far not succeeded and, unfortunately, does not
seem to be
usable from source() i.e., cannot be interpreted but must be built first.
JN
Example using<<-
rm(list=ls())
optstart<-function(npar){ # create structure for optimization computations
# npar is number of parameters ?? test??
OPCON<<-list(MAXIMIZE=TRUE, PARSCALE=rep(1,npar), FNSCALE=1,
KFN=0, KGR=0, KHESS=0)
# may be other stuff
ls(OPCON)
}
The code above creates OPCON as a global variable; that's dangerous, if
you have multiple different optimizers potentially being used.
add1<-function(){
OPCON$KFN<<-1+OPCON$KFN
test<-OPCON$KFN
}
OPCON<<-list(MAXIMIZE=TRUE, PARSCALE=rep(1,4), FNSCALE=1,
KFN=0, KGR=0, KHESS=0)
ls(OPCON)
print(add1())
print(add1())
print(ls.str())
rm(OPCON) # Try to remove the scratchpad
print(ls())
tmp<-readline("Now try from within a function")
setup<-optstart(4) # Need to sort out how to set this up appropriately
cat("setup =")
print(setup)
print(add1())
print(add1())
rm(OPCON) # Try to remove the scratchpad
======================
Example (failing) using new.env:
rm(list=ls())
optstart<-function(npar){ # create structure for optimization computations
# npar is number of parameters ?? test??
OPCON<-new.env(parent=globalenv())
OPCON<-list(MAXIMIZE=TRUE, PARSCALE=rep(1,npar), FNSCALE=1,
KFN=0, KGR=0, KHESS=0)
This failed because the second assignment wiped out the first: you
created a new environment, then threw it away when you assigned a list
to OPCON. The other problem with this approach is that you never saved
OPCON anywhere, so when optstart() was done, it would disappear.
Hadley suggested using a reference class, and Bill suggested using an
environment explicitly; those are both possible alternatives. My
version creates an environment but never names it; it's the environment
of the add1() function and other functions defined within makethem().
I'd say the more formal versions they suggested would be better if you
had a longer (or open-ended) list of possible functions you wanted to
work with, or if you wanted to pass your OPCON to the user to manipulate.
Duncan Murdoch
# may be other stuff
ls(OPCON)
}
add1<-function(){
OPCON$KFN<-1+OPCON$KFN
test<-OPCON$KFN
}
OPCON<-new.env(parent=globalenv())
OPCON<-list(MAXIMIZE=TRUE, PARSCALE=rep(1,4), FNSCALE=1,
KFN=0, KGR=0, KHESS=0)
ls(OPCON)
print(add1())
print(add1())
print(ls.str())
rm(OPCON) # Try to remove the scratchpad
print(ls())
tmp<-readline("Now try from within a function")
setup<-optstart(4) # Need to sort out how to set this up appropriately
cat("setup =")
print(setup)
print(add1())
print(add1())
rm(OPCON) # Try to remove the scratchpad
______________________________________________
[email protected] mailing list
https://stat.ethz.ch/mailman/listinfo/r-help
PLEASE do read the posting guide http://www.R-project.org/posting-guide.html
and provide commented, minimal, self-contained, reproducible code.
______________________________________________
[email protected] mailing list
https://stat.ethz.ch/mailman/listinfo/r-help
PLEASE do read the posting guide http://www.R-project.org/posting-guide.html
and provide commented, minimal, self-contained, reproducible code.