【问题标题】:dynamic aggregations with data.table in R using derived column names使用派生列名在 R 中使用 data.table 进行动态聚合
【发布时间】:2014-04-28 09:05:05
【问题描述】:

我有这个具有不同列类型的 data.table。

我事先不知道列名,我只想为特定类型的列(比如数字)生成聚合。如何使用 data.table 实现这一点?

例如,考虑下面的代码:

dt <- data.table(ch=c('a','b','c'),num1=c(1,3,6), num2=1:9)

需要创建一个接受上述data.table的函数,并自动对按字符字段分组的数字字段执行计算(比如num1上的sum和num2上的mean,by ch)。如何动态实现?

我们可以使用sapply(dt, is.numeric) 找出数字列,但它以字符串形式提供列名 - 不知道如何将其插入 data.table。帮助表示赞赏。下面的代码给出了所需的概念 - 但不起作用

DoSomething <- function(dt)
{
    numCols <- names(dt)[sapply(dt, is.numeric)]
    chrCols <- names(dt)[sapply(dt, is.character)]
    dt[,list(sum(numCols[1]), mean(numCols[2])), by=(chrCols), with=F]
}

【问题讨论】:

    标签: r data.table


    【解决方案1】:

    您可以使用.SDcols 参数来实现它。见例子。

    require(data.table)
    
    dt <- data.table(ch=c('a','b','c'), num1=c(1,3,6), num2=1:9)
    
    DoSomething <- function(dt) {
        numCols <- names(dt)[sapply(dt, is.numeric)]
        chrCols <- names(dt)[sapply(dt, is.character)]
        dt[, list(sum(.SD[[1]]), mean(.SD[[2]])), by = chrCols, .SDcols = numCols]
    }
    
    DoSomething(dt)
    

    【讨论】:

    • 效果很好。我将研究这个 .SD 的工作原理。感谢您指出正确的方向。
    • 快速跟进问题:如何保留dt[,,] 之后的所有列我在 dt 中还有其他因子列在此之后丢失。
    • @GopalakrishnaPalem,你想怎么看他们?作为by 变量?
    • 好的。这是问题所在。我的 dt 由 {num1, num2, ch, fac1} 类型 {numeric, numeric, character, factor} 的四列组成。我的问题是 - 比如说,我需要为所有数字添加 +1 并保持其他所有内容相同。所以它是一个转变。现在感谢您的 .SDcols 提示,我可以使用 dt[,lapply(.SD,function(x) x+1), .SDcols=c('num1','num2')] 为我的所有号码添加 +1。在这种特殊情况下,我没有使用by,因为它不是聚合(下一步我必须这样做)。但是在这个增量之后,我在输出中没有更多的 ch 或 fac1 列用于聚合。任何指针,请。
    • @GopalakrishnaPalem 有一个解决方案。如果您可以就此提出一个新问题,最好的办法是,因为如果当前问题超出了范围。
    【解决方案2】:

    @djhurio 为您的问题提供了一个很好的解决方案。

    data.table 中的.SD.SDcols 提供您想要的。

    如果您在不同的列之间执行相同的计算,您可以尝试以下代码。

    require(data.table)
    
    dt <- data.table(ch=c('a','b','c'), num1=c(1,3,6), num2=1:9)
    
    DTfunction <- function(dt){
        numCols <- names(dt)[sapply(dt, is.numeric)]
        chrCols <- names(dt)[sapply(dt, is.character)]
        dt <- dt[, lapply(.SD, mean), by = (chrCols), .SDcols = (numCols)]
    }
    

    可爱的代码。不是吗? :)

    【讨论】:

    • 请检查您的代码。 lapplymean 都没有 by 参数。
    • 我猜他的意思是,dt[, lapply(.SD, mean), by = chrCols, .SDcols = (numCols)]
    • @GopalakrishnaPalem 是的。在此示例中,DTfunction 返回 NULL
    猜你喜欢
    • 1970-01-01
    • 2013-11-19
    • 1970-01-01
    • 1970-01-01
    • 2013-02-02
    • 1970-01-01
    • 2014-09-02
    • 2020-07-01
    • 2020-01-19
    相关资源
    最近更新 更多