Como usar um número desconhecido de colunas-chave em um data.table

Eu quero fazer o mesmo que explicadoAqui, isto é, adicionar linhas ausentes a um data.table. A única dificuldade adicional que estou enfrentando é que eu quero que o número de colunas-chave, ou seja, aquelas linhas que são usadas para a auto-junção, sejam flexíveis.

Aqui está um pequeno exemplo que basicamente repete o que é feito no link mencionado acima:

df <- data.frame(fundID   = rep(letters[1:4], each=6),
                 cfType   = rep(c("D", "D", "T", "T", "R", "R"), times=4),
                 variable = rep(c(1,3), times=12),
                 value    = 1:24)
DT <- as.data.table(df)
idCols <- c("fundID", "cfType")
setkeyv(DT, c(idCols, "variable"))
DT[CJ(unique(df$fundID), unique(df$cfType), seq(from=min(variable), to=max(variable))), nomatch=NA]

O que me incomoda é a última linha. eu queroidCols para ser flexível (por exemplo, se eu usá-lo dentro de uma função), então eu não quero digitarunique(df$fundID), unique(df$cfType) manualmente. No entanto, eu simplesmente não encontro nenhuma solução para isso. Todas as minhas tentativas de dividir automaticamente o subconjunto dedf em vetores, conforme necessárioCJ, falha com a mensagem de erroErro no setkeyv (x, cols, verbose = verbose): A coluna 'V1' é do tipo 'list' que não é (atualmente) permitida como um tipo de coluna de chave.

CJ(sapply(df[, idCols], unique))
CJ(unique(df[, idCols]))
CJ(as.vector(unique(df[, idCols])))
CJ(unique(DT[, idCols, with=FALSE]))

Eu também tentei construir a expressão eu mesmo:

str <- ""
for (i in idCols) {
  str <- paste0(str, "unique(df$", i, "), ")
}
str <- paste0(str, "seq(from=min(variable), to=max(variable))")
str
[1] "unique(df$fundID), unique(df$cfType), seq(from=min(variable), to=max(variable))"

Mas então eu não sei usarstr. Tudo isso falha:

CJ(eval(str))
CJ(substitute(str))
CJ(call(str))

Alguém sabe uma boa solução?

questionAnswers(2)

yourAnswerToTheQuestion