Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- > fibo <- function(n) {
- + if ( n < 2 ) n
- + else fibo(n-1) + fibo(n-2)
- + }
- > system.time(for(i in 0:26) fibo(i))
- user system elapsed
- 7.48 0.00 7.52
- > system.time(sapply(0:26, fibo))
- user system elapsed
- 7.50 0.00 7.54
- > system.time(lapply(0:26, fibo))
- user system elapsed
- 7.48 0.04 7.54
- > library(plyr)
- > system.time(ldply(0:26, fibo))
- user system elapsed
- 7.52 0.00 7.58
- library(snow)
- cl <- makeSOCKcluster(c("localhost","localhost"))
- parSapply(cl, 1:20, get("+"), 3)
- parLapply(cl, x, fun, ...)
- parSapply(cl, X, FUN, ..., simplify = TRUE, USE.NAMES = TRUE)
- parApply(cl, X, MARGIN, FUN, ...)
- parRapply(cl, x, fun, ...)
- parCapply(cl, x, fun, ...)
- > df <- 1:10
- > # *apply example
- > lapply(2:3, function(i) df <- df * i)
- > df
- [1] 1 2 3 4 5 6 7 8 9 10
- > # for loop example
- > for(i in 2:3) df <- df * i
- > df
- [1] 6 12 18 24 30 36 42 48 54 60
- set.seed(1) #for reproducability of the results
- # The data
- X <- rnorm(100000)
- Y <- as.factor(sample(letters[1:5],100000,replace=T))
- Z <- as.factor(sample(letters[1:10],100000,replace=T))
- # the function forloop that averages X over every combination of Y and Z
- forloop <- function(x,y,z){
- # These ones are for optimization, so the functions
- #levels() and length() don't have to be called more than once.
- ylev <- levels(y)
- zlev <- levels(z)
- n <- length(ylev)
- p <- length(zlev)
- out <- matrix(NA,ncol=p,nrow=n)
- for(i in 1:n){
- for(j in 1:p){
- out[i,j] <- (mean(x[y==ylev[i] & z==zlev[j]]))
- }
- }
- rownames(out) <- ylev
- colnames(out) <- zlev
- return(out)
- }
- # Used on the generated data
- forloop(X,Y,Z)
- # The same using tapply
- tapply(X,list(Y,Z),mean)
- > system.time(forloop(X,Y,Z))
- user system elapsed
- 0.94 0.02 0.95
- > system.time(tapply(X,list(Y,Z),mean))
- user system elapsed
- 0.06 0.00 0.06
- > system.time({z <- numeric(1e6); for(i in y) z[i] <- foo(i)})
- user system elapsed
- 3.54 0.00 3.53
- > system.time(z <- lapply(y, foo))
- user system elapsed
- 2.89 0.00 2.91
- > system.time(z <- vapply(y, foo, numeric(1)))
- user system elapsed
- 1.35 0.00 1.36
- foo <- function(x) {
- x <- x+1
- }
- y <- numeric(1e6)
- system.time({z <- numeric(1e6); for(i in y) z[i] <- foo(i)})
- # user system elapsed
- # 4.967 0.049 7.293
- system.time(z <- sapply(y, foo))
- # user system elapsed
- # 5.256 0.134 7.965
- system.time(z <- lapply(y, foo))
- # user system elapsed
- # 2.179 0.126 3.301
- set.seed(1) #for reproducability of the results
- # The data - copied from Joris Meys answer
- X <- rnorm(100000)
- Y <- as.factor(sample(letters[1:5],100000,replace=T))
- Z <- as.factor(sample(letters[1:10],100000,replace=T))
- # an R way to generate tapply functionality that is fast and
- # shows more general principles about fast R coding
- YZ <- interaction(Y, Z)
- XS <- split(X, YZ)
- m <- vapply(XS, mean, numeric(1))
- m <- matrix(m, nrow = length(levels(Y)))
- rownames(m) <- levels(Y)
- colnames(m) <- levels(Z)
- m
- df <- data.frame(id = rep(letters[1:10], 100000),
- value = rnorm(1000000))
- f1 <- function(x)
- tapply(x$value, x$id, sum)
- f2 <- function(x){
- res <- 0
- for(i in seq_along(l <- unique(x$id)))
- res[i] <- sum(x$value[x$id == l[i]])
- names(res) <- l
- res
- }
- library(microbenchmark)
- > microbenchmark(f1(df), f2(df), times=100)
- Unit: milliseconds
- expr min lq median uq max neval
- f1(df) 28.02612 28.28589 28.46822 29.20458 32.54656 100
- f2(df) 38.02241 41.42277 41.80008 42.05954 45.94273 100
- mat <- matrix(rnorm(1000000), nrow=1000)
- f3 <- function(x)
- apply(x, 2, sum)
- f4 <- function(x){
- res <- 0
- for(i in 1:ncol(x))
- res[i] <- sum(x[,i])
- res
- }
- > microbenchmark(f3(mat), f4(mat), times=100)
- Unit: milliseconds
- expr min lq median uq max neval
- f3(mat) 14.87594 15.44183 15.87897 17.93040 19.14975 100
- f4(mat) 12.01614 12.19718 12.40003 15.00919 40.59100 100
- f5 <- function(x)
- colSums(x)
- > microbenchmark(f5(mat), times=100)
- Unit: milliseconds
- expr min lq median uq max neval
- f5(mat) 1.362388 1.405203 1.413702 1.434388 1.992909 100
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement