2017-08-09 11 views
0

dcast.data.tableを使用してデータを再形成しようとしていますが、事前定義された関数リストを使用すると、dcast.data.tableがエラーをスローします。dcast.data.tableの関数リストを使用中にエラーが発生しました

require(data.table) 
require(Hmisc) 

n <- 2 
contributors <- 1:2 
dates <- 2 

DT <- data.table(ID = rep(rep(1:n, contributors), each = dates)) 
DT[, contributor := c(1,1,2,2,2,3)] 
DT[, date := c(1,2,1,1,2,2)] 
DT[, amount := rnorm(.N)] 
DT[, rate := c(1,1,1,3,3,4)] 
DT 
# ID contributor date  amount rate 
# 1: 1   1 1 -1.3888607 1 
# 2: 1   1 2 -0.2787888 1 
# 3: 2   2 1 -0.1333213 1 
# 4: 2   2 1 0.6359504 3 
# 5: 2   2 2 -0.2842529 3 
# 6: 2   3 2 -2.6564554 4 

var.list <- as.list(Cs(amount, rate)) 

collapse <- function(x) paste(x, collapse = ',') 
fun.list <- list(sum, collapse) 

dcast.data.table(data = DT, ID + contributor ~ date, 
       fun.aggregate = fun.list, 
       value.var = var.list, fill = NA) 
# Error in aggregate_funs(fun.call, lvals, sep, ...) : 
# When 'fun.aggregate' and 'value.var' are both lists, 'value.var' must be either of length =1 or =length(fun.aggregate). 

しかし、長さが同じである:私はなぜこれを知っていただきたいと思い

dcast.data.table(data = DT, ID + contributor ~ date, 
       fun.aggregate = list(sum, collapse), 
       value.var = var.list, fill = NA) 

# ID contributor amount_sum_1 amount_sum_2 rate_collapse_1 rate_collapse_2 
# 1: 1   1 -1.3888607 -0.2787888    1    1 
# 2: 2   2 0.5026291 -0.2842529    1,3    3 
# 3: 2   3   NA -2.6564554    NA    4 

fun.aggregatedcastに直接定義されて
length(var.list) == length(fun.list) 
# [1] TRUE 

、その後、何の問題もありませんこのエラーを回避するにはどうすればいいですか?dcast.data.tableで定義済みの関数リストを使用してください。何が価値がある、あなたがそうのように、dcastへのリテラルのリストを提供し、ユーザーを渡すためにsubstitute()を使用して、手でdcastへの呼び出しを構築することができますについては

+0

[こちら](https://github.com/Rdatatable/data.table/issues/1369)が報告されているようです – akrun

答えて

1

z = as.data.table(expand.grid(a=LETTERS[1:3],b=1:3,c=5:6,d=3:4,stringsAsFactors =FALSE))[sample(36,9)] 

myfun = function(DT,fmla,funs,vars) 
    do.call("dcast",list(zz,a~.,fun=substitute(funs),value.var = list('c','d'))) 

myfun(z,a~.,list(sum,mean),list('c','d')) 

>  a c_sum d_mean 
> 1: A 24 3.500000 
> 2: B 10 3.500000 
> 3: C 18 3.333333 

しかし、あなたユーザー(つまり、誰でもこの例ではmyfun()を呼び出す)はリストリテラルを提供する必要があります。これはリストリテラルを期待するfun.aggregateに渡された引数のASTを辿るdcastの内部を回らないためです。

関連する問題