[R-br] Funcionamento (implementação) da função apply (lapply) em loops

Fernando Henrique Toledo fernandohtoledo em gmail.com
Terça Junho 14 09:48:45 BRT 2011


Que bonita demostração Benilton, vou fazer a liçãod e casa aqui, valeu!

att,
FH

2011/6/14 Benilton Carvalho <beniltoncarvalho em gmail.com>

> Atualmente, a ideia de *apply() ser mais rapido que for() nao eh
> exatamente verdadeira.
>
> A diferenca essencial (as far as users care) entre ambas eh que a
> familia *apply cria um objeto de resposta para cada elemento de
> entrada, ao passo que usuarios do for() fazem alocacao da resposta a
> objetos pre-existentes (o que dispara uma copia e, consequentemente,
> faz com que a execucao seja mais lenta).
>
> Veja o exemplo abaixo (mude as dimensoes caso vc nao tenha RAM suficiente):
>
> nc <- 1e6
> nr <- 200
>
> ## com sapply
> set.seed(1)
> t0 <- system.time(res0 <- sapply(1:nr, function(x) rnorm(nc)))
>
> ## com for() usando o q a maioria de usuarios faz...
> set.seed(1)
> t1 <- system.time({res1 <- NULL; for (i in 1:nr) res1 <- cbind(res1,
> rnorm(nc))})
> all.equal(res0, res1)  ## deve ser TRUE
> rm(res0)
>
> ## com for() mais eficiente
> set.seed(1)
> t2 <- system.time({res2 <- matrix(NA, nc=nr, nr=nc); for (i in 1:nr)
> res2[,i] <- rnorm(nc)})
> all.equal(res1, res2) ## deve ser TRUE
> rm(res1); gc()
>
> ## com lapply()
> set.seed(1)
> t3 <- system.time(res3 <- do.call(cbind, lapply(1:nr, function(x)
> rnorm(nc))))
> all.equal(res2, res3) ## deve ser TRUE
> rm(res2, res3); gc()
>
> ## visualizando tempos
> message(sprintf('sapply...........: %2.4f', t0[3]))
> message(sprintf('for() usual......: %2.4f', t1[3]))
> message(sprintf('for() pre-aloc..: %2.4f', t2[3]))
> message(sprintf('do.call+lapply: %2.4f', t3[3]))
>
> Os resultados que obtive na minha maquina sao:
>
> sapply...........: 20.5400
> for() usual......: 207.3900
> for() pre-aloc..: 21.7730
> do.call+lapply: 18.3960
>
> Take-home messages:
>
> 1) for() mais lento e' fato qdo a programacao e' ineficiente;
> 2) lapply() e' sempre mais eficiente que sapply()
>
> Take-home exercise: repita o for() com pre-alocacao usando listas,
> combinando o resultado com do.call()... Isso e' tao rapido quanto o
> do.call+lapply (na verdade, na minha execucao, ele eh ainda
> ligeiramente mais rapido... levando 18.385s)...
>
> b
>
> 2011/6/14 Junior Beleti <beleti.junior em gmail.com>:
> > Boa noite,
> >
> > gostaria de entender o funcionamento da função apply, mais precisamente
> > lapply, para loops.
> >
> > Já conheço a descrição de seu funcionamento:
> >
> > ‘lapply’ returns a list of the same length as ‘X’, each element of which
> is
> > the result of applying ‘FUN’ to the corresponding element of ‘X’.
> >
> >
> > Mas o que eu gostaria de saber é como ele funciona em sua essência. Por
> > exemplo, utilizar um lapply ao invés de um loop "for" é mais rápido.
> > Eu gostaria de saber o porque, ou seja, como o lapply é implementado.
> >
> > Não sei se fui claro, mas gostaria de encontrar a implementação da função
> > lapply, o que não encontrei no diretório do pacote "base".
> >
> > Se alguém puder ajudar.
> >
> > Também peço desculpas por não ter dado grandes contribuições para a
> lista,
> > mas creio ter mais experiência em programação (lógica) de fato, do que no
> > ambiente R.
> >
> > Obrigado.
> >
> > --
> > Carlos Roberto Beleti Junior
> > Mestrado em Ciência da Computação
> > Departamento de Informática
> > Universidade Estadual de Maringá
> >
> > _______________________________________________
> > R-br mailing list
> > R-br em listas.c3sl.ufpr.br
> > https://listas.inf.ufpr.br/cgi-bin/mailman/listinfo/r-br
> > Leia o guia de postagem (http://www.leg.ufpr.br/r-br-guia) e forneça
> código
> > mínimo reproduzível.
> >
>
>
>
> --
> Successful people ask better questions, and as a result, they get
> better answers. (Tony Robbins)
> _______________________________________________
> R-br mailing list
> R-br em listas.c3sl.ufpr.br
> https://listas.inf.ufpr.br/cgi-bin/mailman/listinfo/r-br
> Leia o guia de postagem (http://www.leg.ufpr.br/r-br-guia) e forneça
> código mínimo reproduzível.
>
-------------- Próxima Parte ----------
Um anexo em HTML foi limpo...
URL: <http://listas.inf.ufpr.br/pipermail/r-br/attachments/20110614/b43abbd2/attachment.html>


Mais detalhes sobre a lista de discussão R-br