将项目返回data.table
时,如果它们自动采用变量名称会很好。怎么做到这一点?这就是我的意思:
require(data.table)
x = data.table(a=1:10, id=1:2)
x[,{s = sum(a); p=prod(a); y = sqrt(abs(s*p)); z = y+1; list(y, z)},by=id]
# id V1 V2
#1: 1 25 945
#2: 2 30 3840
如果columsn标记为V1
和V2
,那么代替s
和p
会很好。在这里做这件事并不重要,但如果你有20列,那将成为一个真正的痛苦。关于如何做到这一点的任何想法?
编辑:我改变了问题,以明确我为什么不做列表(名称=值)
答案 0 :(得分:3)
请原谅我,如果我遗漏了某些内容......但是list
的{{1}}语法不是您正在寻找的内容吗?它更简洁,更清晰恕我直言。
data.table
您还可以将此x[,
list(s = sum(a),
p = prod(a)),
by=id]
# id s p
# 1: 1 25 945
# 2: 2 30 3840
建立为list
和expression
。
eval
然后可以将其扩展为一个函数(使用foo <- expression(list(s=sum(a), p=prod(a)))
x[, eval(foo), by=id]
中的as.quoted
而不是使其方便):
plyr
......但是有龙!
:
expression_maker <- function(funs, cols, names) {
require(plyr)
list_contents <- paste0(names, '=', funs, '(', cols, ')', collapse=',')
as.quoted(paste('list(', list_contents, ')'))[[1]]
}
output <- expression_maker(funs=c('sum', 'prod'), cols=c('a', 'a'), names=c('s', 'p'))
x[, eval(output), by=id]
我会在函数中执行此操作并直接返回x[,{s = sum(a); p=prod(a); y = sqrt(abs(s*p)); z = y+1; list(y, z)},by=id]
:
data.table
答案 1 :(得分:2)
另外两个答案的混音 - 在列表中命名:
x[,{s = sum(a); p=prod(a); y = sqrt(abs(s*p)); z = y+1;
list(s = y, p = z)}, by=id]
或构建data.table
x[,{s = sum(a); p=prod(a); y = sqrt(abs(s*p)); z = y+1;
data.table(y, z)}, by=id]
这是使用Hmisc
的另一个选项(这比手动命名慢,但可能比data.table
更快):
library(Hmisc)
x[,{s = sum(a); p=prod(a); y = sqrt(abs(s*p)); z = y+1;
llist(y, z)}, by=id]
答案 2 :(得分:1)
如果你有大量的可用物品并且你正在寻找一种程序化方法来解决这个问题,你可以将列的名称放在一个向量中,然后将sapply
与.SDcols
一起使用
例如:
## sample data
set.seed(7)
DT <- as.data.table(matrix(round(runif(130, 1, 100)), ncol=26))
setnames(DT, LETTERS)
## These are the columns we will compute on
Cols <- c("A", "G", "M", "W", "Z")
DT[,sapply(.SD,mean),.SDcols=Cols]
# A G M W Z
# 25.0 41.2 55.6 43.0 56.0
如果要计算每个变量的不同函数,请使用标准list(nm=function(x))