Un collega mi ha chiesto questo, e ho faticato con esso.passaggio di espressioni a curve() all'interno di una funzione
Supponiamo di voler definire una funzione che prende un'espressione (diciamo x^2
per concretezza) come argomento e passa tale argomento a curve()
.
Se voglio fare questo nel modo più semplice, ho solo eseguito
curve(x^2,from=0,to=3)
e funziona benissimo.
Supponiamo che io cerco di impostare una funzione wrapper (diciamo che ci sono altre cose che voglio fare all'interno della confezione, oltre a tracciare la curva):
f <- function(g) {
curve(g,from=0,to=3)
}
Questo funziona se mi passa una funzione:
f(function(x) x^2)
fallisce se provo a passare x^2
, quando R cerca di valutare l'espressione:
f(x^2)
## Error in eval(expr, envir, enclos) (from #2) : object 'x' not found
posso provare di prevenire questo utilizzando substitute
all'interno della funzione:
f0 <- function(g) {
str(substitute(g))
curve(substitute(g),from=0,to=3)
}
f0(x^2)
## language x^2
## Error in curve(substitute(g), from = 0, to = 3) (from #3) :
## 'expr' must be a function, or a call or an expression containing 'x'
OK, che suggerisce forse dovrei provare
f <- function(g) {
h <- as.expression(substitute(g))
str(h)
curve(as.expression(substitute(g)),from=0,to=3)
}
f(x^2)
## expression(x^2)
## Error in curve(as.expression(substitute(g)), from = 0, to = 3) (from #4) :
## 'expr' must be a function, or a call or an expression containing 'x'
Per quel che vale,
- questo fallisce in modo diverso con
curve(h,...)
("funzioneh
non trovata") - fallisce nello stesso modo se
as.call()
è sostituitoas.expression()
curve()
non funziona su espressioni in ogni caso:
curve(expression(x^2),from=0,to=1)
## Error in curve(expression(x^2), from = 0, to = 1) :
## 'expr' did not evaluate to an object of length 'n'
se provo debug curve()
per vedere cosa sta succedendo, Abbiamo:
sexpr <- substitute(expr)
...
if (!((is.call(sexpr) || is.expression(sexpr)) && xname %in%
all.vars(sexpr)))
stop(...)
Qui sexpr
è substitute(g)
, che non riesce il test xname %in% all.vars(sexpr)
...
Qualche idea su come gestirlo?
Hai dato a "do.call" un colpo? Sembra che funzioni come con 'lm',' glm', ecc. –