【问题标题】:Speeding up an R for loop to paste multiple variables together加速 R for 循环以将多个变量粘贴在一起
【发布时间】:2018-07-12 20:03:34
【问题描述】:

我是新来的,但需要一些帮助。我有一个数据框列表,对于列表中的每个元素(即 data.frame),我想快速将数据集中的一列粘贴到同一数据集中的多个其他列,仅用句点分隔(“ 。”)。

所以如果我在数据框列表中有一组数据:

list1[[1]]

A  B  C
2  1  5
4  2  2

那么我想要以下结果:

list1[[1]]

 A    B   C
2.5  1.5  5
4.2  2.2  2  

其中 C 分别粘贴到 A 和 B。然后,我希望对列表中的每个数据框都进行此操作。

我尝试了以下方法:

pasteX<-function(df) {for (i in 1:dim(df)[2]-1) {
df[,i]<-as.numeric(sprintf("%s.%s", df[,i], df$C))
}
return(df)}
list2<-lapply(list1, pasteX)

但是对于较大的矩阵和列表,这种方法非常缓慢。有什么建议可以让这段代码更快吗?谢谢!

【问题讨论】:

  • 欢迎。理想情况下,以更易于阅读的方式提供您的数据:stackoverflow.com/questions/5963269/…
  • 啊,谢谢你的分享……从现在开始我会更加注意我如何呈现我的数据和问题!

标签: r


【解决方案1】:

假设一切都是整数

lapply(list1, function(x){
    x[,-3] <- x[,-3] + x[,3]/10
    x})

【讨论】:

    【解决方案2】:

    我们可以使用Map

    list1[[1]][-3] <- Map(function(x, y) as.numeric(sprintf('%s.%s', x, y)), 
                         list1[[1]][-3], list1[[1]][3])
    

    如果有很多数据集,使用lapply循环,将前两列转换为matrix并粘贴到第三列,更新输出,并返回数据集

    lapply(list1, function(x)  {
         x[1:2] <- as.numeric(sprintf('%s.%s', as.matrix(x[1:2]), x[,3]));
         x })
    #[[1]]
    #    A   B C
    #1 2.5 1.5 5
    #2 4.2 2.2 2
    

    或者使用tidyverse

    library(tidyverse)
    map(list1, ~ .x %>%
                   mutate_at(1:2, funs(as.numeric(sprintf('%s.%s', ., C)))))
    

    data.table

    library(data.table)
    lapply(list1,  function(x) setDT(x)[, (1:2) := 
         lapply(.SD, function(x) as.numeric(sprintf('%s.%s', x, C))) ,
                 .SDcols = 1:2][])
    

    【讨论】:

    • 谢谢,@akrun!这很有用,我现在将尝试实现它,看看它能给我带来多大的提升。
    • @zeekster26 没问题。如果您正在检查基准,我还使用 data.table 方法进行了更新。请同时检查
    • 甜蜜!非常感谢......我正在尝试一种 data.table 方法,但它有点错误。
    • 地图解决方案是迄今为止最快的!
    【解决方案3】:

    试试这个:

    df <- data.frame(a = c(1,2,3), b = c(3,2,1), c = c(2,1,1))
    
    
    pastex <- function(x){
     m<-  sapply(df[,1:2], function(x) as.numeric(paste(x, df$c, sep = '.')))
     m <- as.data.frame(m)
     m <- cbind(m, df["c"])
     return(m)
    }
    
    mylist <- list(df1 = df, df2 = df)
    
    lapply(mylist, pastex)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-05-07
      • 1970-01-01
      • 2016-01-18
      • 1970-01-01
      • 1970-01-01
      • 2019-10-25
      相关资源
      最近更新 更多