【问题标题】:Bind data.table with diff rows such that the shorter dataset repeats the last row将 data.table 与差异行绑定,以便较短的数据集重复最后一行
【发布时间】:2019-06-14 12:49:24
【问题描述】:

我正在尝试将 R 中的两个数据集与 diff nrows 绑定,以便较短的数据集重复最后一行,直到由“BY”变量分组的其他数据集的长度相等

假设下面是两个数据集


dt1<- data.table(Student = c(6,6,6,7,7),

            RollNum1 = c(49,69,44,86,39),

            Marks1= c(8,9,10,8,5))

dt2<- data.table(Student = c(6,6,6,6,6,6,6,6,6,7,7,7,7,7,7,7),

             RollNum2 = c(58,69,45,38,88,73,33,99,29,58,31,55,58,44,56,89),

             Marks2= c(8,9,10,3,5,7,8,8,9,6,9,5,9,3,4,8))


合并应该给出以下结果

Student   RollNum1  Marks1  RollNum2  marks2
6   49    8   58  8
6   69    9   69  9
6   44    10    45  10
6   44    10    38  3
6   44    10    88  5
6   44    10    73  7
6   44    10    33  8
6   44    10    99  8
6   44    10    29  9
7   86    8   58  6
7   39    5   31  9
7   39    5   55  5
7   39    5   58  9
7   39    5   44  3
7   39    5   56  4
7   39    5   89  8

我能够从另一个帖子中获取单个学生值,但我不知道如何按学生分组并运行它,然后附加以获得最终结果。

运行单个学生值 e.x - 6 :下面是代码。

LastRowrep<-as.data.frame(matrix(rep(unlist(dt1[nrow(dt1),]),times=nrow(dt2)-nrow(dt1)),ncol = ncol(dt1), byrow = T))

colnames(LastRowrep)<-colnames(dt1)

cbind(rbind(dt1,LastRowrep),dt2)

但是为不同的学生值运行这个不会按组值绑定

【问题讨论】:

  • 感谢 Carles 的第一点!我仍然对如何为不同的学生价值观获取它感到困惑。

标签: r data.table


【解决方案1】:

另一种使用熔化和铸造的 data.table 方法。 铸造后,用 locf 填写 NA。在 data.table 的开发版本中,实现了 nafill,但我使用 zoo::na.locf 直到 1.12.3 进入最终版本

DT <- rbind( melt(dt1, id.vars = "Student"), melt(dt2, id.vars = "Student") )[, rowid := rowid( Student, variable )]
ans <- dcast( DT, rowid + Student ~ variable, value.var = "value" )
setorder( ans, Student)
zoo::na.locf(ans, na.rm=FALSE)[, rowid := NULL][]

#    Student RollNum1 Marks1 RollNum2 Marks2
# 1:       6       49      8       58      8
# 2:       6       69      9       69      9
# 3:       6       44     10       45     10
# 4:       6       44     10       38      3
# 5:       6       44     10       88      5
# 6:       6       44     10       73      7
# 7:       6       44     10       33      8
# 8:       6       44     10       99      8
# 9:       6       44     10       29      9
#10:       7       86      8       58      6
#11:       7       39      5       31      9
#12:       7       39      5       55      5
#13:       7       39      5       58      9
#14:       7       39      5       44      3
#15:       7       39      5       56      4
#16:       7       39      5       89      8

【讨论】:

    【解决方案2】:
    dt1[, nrows := dt2[, .(rows = .N), by = Student][.SD, on = "Student", rows]]
    dt1 <- dt1[, .SD[c(1:.N, rep(.N, nrows[1] - .N))], by = Student]
    cbind(dt1[, !"nrows"], dt2[, !"Student"])
    
    #     Student RollNum1 Marks1 RollNum2 Marks2
    #  1:       6       49      8       58      8
    #  2:       6       69      9       69      9
    #  3:       6       44     10       45     10
    #  4:       6       44     10       38      3
    #  5:       6       44     10       88      5
    #  6:       6       44     10       73      7
    #  7:       6       44     10       33      8
    #  8:       6       44     10       99      8
    #  9:       6       44     10       29      9
    # 10:       7       86      8       58      6
    # 11:       7       39      5       31      9
    # 12:       7       39      5       55      5
    # 13:       7       39      5       58      9
    # 14:       7       39      5       44      3
    # 15:       7       39      5       56      4
    # 16:       7       39      5       89      8
    

    【讨论】:

      【解决方案3】:

      如果你想要 dplyr 方法,这里就是。

      library(tidyverse)
      dt1 = dt1 %>% gather(key, value, -Student)
      dt2 = dt2 %>% gather(key, value, -Student)
      
      dt3 = bind_rows(dt1, dt2) %>% 
        group_by(Student, key) %>% 
        mutate(id = seq(n())) %>% 
        spread(key, value) %>% 
        fill(c(Marks1:RollNum2)) %>% 
        select(-id)
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-09-04
        相关资源
        最近更新 更多