代码之家  ›  专栏  ›  技术社区  ›  Stefan

选择或子集列和不为零的变量

  •  3
  • Stefan  · 技术社区  · 6 年前

    我想在列和不为零但也为零的数据帧中选择或子集变量 保留其他因素变量 select_if() 在变量子集上使用 dplyr :

    df <- data.frame(
      A = c("a", "a", "b", "c", "c", "d"),
      B = c(0, 0, 0, 0, 0, 0),
      C = c(3, 0, 0, 1, 1, 2),
      D = c(0, 3, 2, 1, 4, 5)
    )
    
    require(dplyr)
    df %>% 
      select_if(funs(sum(.) > 0))
    
    #Error in Summary.factor(c(1L, 1L, 2L, 3L, 3L, 4L), na.rm = FALSE) : 
    #  ‘sum’ not meaningful for factors
    

    B, C, D 这是可行的,但我没有变量 A :

    df %>% 
      select(-A) %>% 
      select_if(funs(sum(.) > 0)) -> df2
    df2
    #  C D
    #1 3 0
    #2 0 3
    #3 0 2
    #4 1 1
    #5 1 4
    #6 2 5
    

    我可以这么做 cbind(A = df$A, df2) 但由于我有一个包含3000行和200列的数据集,我担心这可能会引入错误(例如,如果值排序不同)。

    尝试子集变量 B、 C、D sum() 函数也不起作用:

    df %>% 
      select_if(funs(sum(names(.[2:4])) > 0))
    #data frame with 0 columns and 6 rows
    
    2 回复  |  直到 6 年前
        1
  •  13
  •   mt1022    6 年前

    试试这个:

    df %>% select_if(~ !is.numeric(.) || sum(.) != 0)
    #   A C D
    # 1 a 3 0
    # 2 a 0 3
    # 3 b 0 2
    # 4 c 1 1
    # 5 c 1 4
    # 6 d 2 5
    

    理由是 || 如果左边是 TRUE

    注:

    • 第二个论点 select_if ~ 有必要告诉我 选择\u if !is.numeric(.) || sum(.) != 0
    • 如@zx8754在下文中所述, is.factor(.) 如果一个人只想保持 factor 柱。

    碱性溶液

    cols <- c('B', 'C', 'D')
    cols.to.keep <- cols[colSums(df[cols]) != 0]
    df[!names(df) %in% cols || names(df) %in% cols.to.keep]
    
        2
  •  3
  •   Agile Bean    4 年前

    这里是一个更新,为每个人谁想要使用新的 dplyr 1.0.0 没有范围变量(比如 select_if 如@mt1022所示,但已弃用):

    df %>% 
      select(where(is.numeric)) %>% 
      select(where(~sum(.) != 0))
    

    如果要将两个select语句压缩为一个,则不能通过元素方式来实现 & &&

    df %>% select(where(~ is.numeric(.x) && sum(.x) !=0 ))
    
        3
  •  2
  •   Rage    6 年前

    这是一个使用data.table的解决方案

    df<-data.table(
      A = c("a", "a", "b", "c", "c", "d"),
      B = c(0, 0, 0, 0, 0, 0),
      C = c(3, 0, 0, 1, 1, 2),
      D = c(0, 3, 2, 1, 4, 5)
    )
    
    df2<-df[,lapply(X = .SD,FUN = function(x){sum(as.numeric(x))}),.SDcols = colnames(df)]
    df[,which(is.na(df[1,]) == F),with = F]