【问题标题】:Summarize data frame to return non-NA values along subsets汇总数据框以沿子集返回非 NA 值
【发布时间】:2018-09-08 22:29:10
【问题描述】:

希望有人可以帮助我。我在网上找到了类似的问题,但我所见过的例子都没有完全符合我的要求或在我的数据结构上工作。

我需要沿数据子集从数据帧中删除 NA,并将剩余的 NA 值压缩到每个数据子集的行中。

例子:

#create example data
a <- c(1, 1, 1, 2, 2, 2) #this is the subsetting variable in the example
b <- c(NA, NA, "B", NA, NA, "C") #max 1 non-NA value for each subset
c <- c("A", NA, NA, "A", NA, NA)
d <- c(NA, NA, 1, NA, NA, NA) #some subsets for some columns have all NA values

dat <- as.data.frame(cbind(a, b, c, d)) 

> desired output
  a b c    d
  1 B A    1
  2 C A <NA>

经验法则: 1)需要从每列中删除NA值 2) 沿数据子集循环(上例中的“a”列) 3) 对于每个子集,所有列最多有 1 个非 NA 值,但某些列可能具有所有 NA 值

想法:

  • lapply 或 dplyr 可能有助于沿所有列循环
  • na.omit 可能很有帮助,如果子集列包含所有条目 可以忽略行(类似于 as.data.frame(lapply(dat.admin, na.omit)))。如果某些子集不返回任何非 NA 值,则将 lapply 输出返回到数据框时出现问题
  • x[which.min(is.na(x))] 如果费力地应用于每个单独的列,则可以有效地实现这一点

感谢任何帮助以将最终部分放在一起!谢谢!

【问题讨论】:

    标签: r dplyr lapply


    【解决方案1】:

    使用dplyr::summarise_all 可以实现一个解决方案。数据需要在a 上为group_by

    library(dplyr)
    
    dat %>%
      group_by(a) %>%
      summarise_all(funs(.[which.min(is.na(.))]))
    # # A tibble: 2 x 4
    #    a      b      c      d     
    #   <fctr> <fctr> <fctr> <fctr>
    # 1   1      B      A      1     
    # 2   2      C      A      <NA>  
    

    【讨论】:

    • 谢谢!我决定使用这个,因为语法对我来说最有意义。
    【解决方案2】:

    不确定这是否是您要查找的内容,但这可能对您有用。它至少复制了您正在寻找的小样本输出:

    library(dplyr)
    library(tidyr)
    
    dat %>% 
      filter_at(vars(b:c), any_vars(!is.na(.))) %>% 
      group_by(a) %>% 
      fill(b) %>% 
      fill(c) %>% 
      filter_at(vars(b:c), all_vars(!is.na(.)))
    
    # A tibble: 2 x 4
    # Groups:   a [2]
           a      b      c      d
      <fctr> <fctr> <fctr> <fctr>
    1      1      B      A      1
    2      2      C      A     NA
    

    你也可以只使用dplyr:

    dat %>%
      group_by(a) %>%
      summarise_each(funs(first(.[!is.na(.)])))  
    

    【讨论】:

      【解决方案3】:

      data.tablena.omit 的解决方案

      library(data.table)
      merge(setDT(dat)[,a[1],keyby=a], setDT(dat)[,na.omit(.SD),keyby=a],all.x=TRUE)
      

      我觉得merge语句可以改进

      【讨论】:

      • 感谢您的帮助!这确实按预期工作 - 谢谢!
      猜你喜欢
      • 2018-04-23
      • 1970-01-01
      • 2021-07-07
      • 2019-03-19
      • 1970-01-01
      • 1970-01-01
      • 2022-12-12
      • 2021-06-30
      • 1970-01-01
      相关资源
      最近更新 更多