Usando get inside lapply, dentro de uma função
isso pode parecer uma pergunta excessivamente complicada, mas isso me deixa um pouco louco por um tempo. É também por curiosidade, porque eu já tenho uma maneira de fazer o que preciso, por isso não é tão important
No R, preciso de uma função para retornar um objeto de lista nomeada com todos os argumentos e valores inseridos pelo usuário. Para isso, criei este código (exemplo de brinquedo):
foo <- function(a=1, b=5, h='coconut') {
frm <- formals(foo)
parms <- frm
for (i in 1:length(frm))
parms[[i]] <- get(names(frm)[i])
return(parms)
}
Então, quando isso for solicitado:
> foo(b=0)
$a
[1] 1
$b
[1] 0
$h
[1] "coconut"
Este resultado é perfeito. O problema é que, quando tento usarlapply
com o mesmo objetivo, para ser um pouco mais eficiente (e elegante), não funciona como eu quero:
foo <- function(a=1, b=5, h='coconut') {
frm <- formals(foo)
parms <- lapply(names(frm), get)
names(parms) <- names(frm)
return(parms)
}
O problema está claramente no ambiente em queget
avalia seu primeiro argumento (uma cadeia de caracteres, o nome da variável). Isso eu sei em parte da mensagem de erro:
> foo(b=0)
Error in FUN(c("a", "b", "h")[[1L]], ...) : object 'a' not found
e também, porque quando .GlobalEnv
ambiente existem objetos com os nomes corretos, foo retorna seus valore
> a <- 100
> b <- -1
> h <- 'wallnut'
> foo(b=0)
$a
[1] 100
$b
[1] -1
$h
[1] "wallnut"
Obviamente, comoget
por padrão é avaliado noparent.frame()
, procura os objetos no.GlobalEnv
ambiente, em vez do da função atual. Isso é estranho, pois isso não acontece com a primeira versão da função.
Tentei muitas opções para fazer a funçãoget
para avaliar no ambiente certo, mas não foi possível fazer isso corretamente (tenteipos=-2,0,1,2
eenvir=NULL
como opções).
Se alguém souber um pouco mais do que eu sobre ambientes, especialmente nesses casos "estranhos", eu adoraria saber como resolver iss
Obrigado pelo seu tempo
Juan