3

のリストがありdata.framesます。各 data.frame 内で、グループ化 ( z) 関数を実行して分割し、結果をまとめてから、ネストされたのすべての結果をlapplydata.frame にまとめて、結果data.frameのリストを 1 つにフラット化します。 data.frame.

library(plyr)
df <- data.frame(x = sample(1:200, 30000, replace = TRUE), 
                y = sample(1:200, 30000, replace = TRUE), 
                z = sample(LETTERS, 30000, replace = TRUE))

alist <- list(df,df,df) # longer in real life
answer <- lapply(alist, function(q) {
    a <- split(q,q$z)
    result.1 <- lapply(a, function(w) {
        neww <- cbind(w[,1],w[,2])
        result.2 <- colSums(neww)
    })
    ldply(result.1)
})
# cor(neww) can actually be a variey of foos I just use cor() for easy reproducibility
ldply(answer)

これには、非常に厳しいメモリ使用量があり、低速でもあります。@Andrie のおかげで、次のように開始する前にワークスペースをクリアする方法を知っています。

 rm(list=setdiff(ls(), "alist"))

しかし、メモリ使用量を減らしてスピードアップを試みるためwに、2番目のジャンクなどの私のアプローチを変更する方法はありますか? lapplyこの場合foo、マトリックスが好きなのでdata.table、私の答えにはなりません。他fooの s では、すべてwが必要になり、クラスは a である必要がありますdata.frame

4

2 に答える 2

9

次のようなことを試してください:

ldply(alist, ddply, "z", summarize, xy.foo = foo(x, y))

必要に応じxy、最終的な data.frame に表示するには、に置き換えsummarizeますtransform。また、使用状況を見て、に置き換える必要がfooあるかもしれません。(x, y)cbind(x, y)

また、コードをプロファイリングすることをお勧めします。最終的にfooは、分割/結合部分ではなく、速度が低下している可能性があります。

于 2013-01-31T12:22:47.007 に答える
6

なぜあなたは使っていないddplyのですllplyか??plyrldply

# Note: @Flodel has a very nice, simple one-line plyr solution
# Please use that.
out <- ldply(alist, function(q) {
    ddply(q, .(z), function(w) {
        neww <- w[, -3]
        result.2 <- colSums(neww) # dummy function
    })
})

最初ldplyは、リストの要素をalist1 つずつ渡します。qしたがって、各時間はdata.frameの各要素に含まれていlistます。では、この中で、 で割りたいと思いzます。入力はqでありdata.frame、出力も である必要があるため、2 番目の引数data.frameを使用してで分割します。ここでは、計算を行い、必要なものを返します (この場合)。として返されます。ddply.(z)zcolSumsldplydata.frame

Data.table解決策:代替の高速data.tableな解決策は、次のように達成できる組み合わせでa を使用するdata.frameことです(@Rolandがコメントでも言及したこと):

require(data.table)
# for creating a group 
group <- vapply(alist, nrow, integer(1))
dt <- data.table(do.call(rbind, alist))
# create group
dt[ , grp := rep(1:3, group)]
setkey(dt, "grp", "z")
# call your function (here column means)
dt[, lapply(.SD, mean), by="grp,z"]
# or if its correlation
dt[, list(cor_x_y = cor(x,y)), by="grp,z"]
于 2013-01-31T12:12:59.953 に答える