【问题标题】:Using select_if with variable name and type conditions使用带有变量名和类型条件的 select_if
【发布时间】:2018-12-18 16:42:04
【问题描述】:

有很多关于使用 dplyr 的select_if 处理多种情况的帖子。但是,无论以何种方式,选择 is.factor 和变量名称到目前为止都对我不起作用。

最终,我想选择 df/tibble 中的所有因素并按名称排除某些变量。

例子:

df <- tibble(A = factor(c(0,1,0,1)), 
             B = factor(c("Yes","No","Yes","No")), 
             C = c(1,2,3,4))

各种尝试:

尝试 1

df %>%
  select_if(function(col) is.factor(col) & !str_detect(names(col), "A"))

Error in selected[[i]] <- .p(.tbl[[tibble_vars[[i]]]], ...) : replacement has length zero

尝试 2

df %>%
      select_if(function(col) is.factor(col) & negate(str_detect(names(col)), "A"))

Error: Can't convert a logical vector to function Call `rlang::last_error()` to see a backtrace

尝试 3

df %>%
  select_if(function(col) is.factor(col) && !str_detect(names(col), "A"))

Error: Only strings can be converted to symbols Call `rlang::last_error()` to see a backtrace

尝试 4

df %>%
  select_if(is.factor(.) && !str_detect(names(.), "A"))

Error in tbl_if_vars(.tbl, .predicate, caller_env(), .include_group_vars = TRUE) : length(.p) == length(tibble_vars) is not TRUE

同时,个别条件工作没有问题:

> df %>%
+     select_if(is.factor)
# A tibble: 4 x 2
  A     B    
  <fct> <fct>
1 0     Yes  
2 1     No   
3 0     Yes  
4 1     No   

> df %>%
+     select_if(!str_detect(names(.), "A"))
# A tibble: 4 x 2
  B         c
  <fct> <dbl>
1 Yes       1
2 No        2
3 Yes       3
4 No        4

问题可能出在这里:

df %>%
  select_if(function(col) !str_detect(names(col), "A"))

Error in selected[[i]] <- .p(.tbl[[tibble_vars[[i]]]], ...) : replacement has length zero

但是,我不知道如何解决这个问题。

【问题讨论】:

  • 使用 %>% 运算符:df %>% dplyr::select_if(is.factor) %>% dplyr::select(-one_of('A'))
  • 我认为自 this question/answer 以来情况没有改变。另见this
  • 我尝试了您提到的帖子中的解决方案,但它们似乎不适用于这个特定问题。我不知道为什么。

标签: r dplyr


【解决方案1】:

也许我遗漏了一些东西,但有什么理由你不能做到以下几点:

df <- tibble(A = factor(c(0,1,0,1)), 
         B = factor(c("Yes","No","Yes","No")), 
         C = c(1,2,3,4))


df %>% select_if(function(col) is.factor(col)) %>% select_if(!str_detect(names(.), "A"))

# A tibble: 4 x 1
B    
<fct>
1 Yes  
2 No   
3 Yes  
4 No   

【讨论】:

  • 是的,这确实是一个显而易见的解决方案。但是,我希望在单个 select_if 语句中压缩它。这是因为知道如何执行此操作对summarise_if 也很有用,您提出的解决方案可能会更尴尬。
【解决方案2】:

只是为了完整性,不确定它是否适合您,但基本 R 可能会在这里为您省点麻烦(第一次,非常快速的镜头):

df[, sapply(names(df), 
  function(coln, df) !grepl("A", coln) && is.factor(df[[coln]]), df = df),
  drop = FALSE]

【讨论】:

    猜你喜欢
    • 2015-11-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-10-17
    相关资源
    最近更新 更多