【问题标题】:Efficiently check the value of multiple variables against a list of values根据值列表有效地检查多个变量的值
【发布时间】:2020-09-12 15:58:53
【问题描述】:

我想创建一个变量来标记多个变量中的一个或多个是否具有特定值。

week  Mon  Tues  Weds  Thurs  Fri  Sat
1     jon  jon   jon   jon    mary mary
2     jane jane  jane  jane   jane jane
3     mary mary  mary  mary   mary jane

我想创建一个二进制变量,用于标记每周的哪一天 == "jon" 或 "mary" 有没有办法在不创建单独检查每个变量的长 ifelse 语句的情况下做到这一点?

week  Mon  Tues  Weds  Thurs  Fri  Sat  flag
1     jon  jon   jon   jon    mary mary 1
2     jane jane  jane  jane   jane jane 0
3     mary mary  mary  mary   mary jane 1

【问题讨论】:

    标签: r dataframe if-statement


    【解决方案1】:

    base 解决方案:

    df$flag <- +(colSums(apply(df[-1], 1, `%in%`, c("jon", "mary"))) > 0)
    

    或者您可以使用c_across() 中的dplyr

    library(dplyr)
    
    df %>%
      rowwise() %>%
      mutate(flag = +any(c_across(-week) %in% c("jon", "mary"))) %>%
      ungroup()
    

    他们都给:

    #    week Mon   Tues  Weds  Thurs Fri   Sat    flag
    # 1     1 jon   jon   jon   jon   mary  mary      1
    # 2     2 jane  jane  jane  jane  jane  jane      0
    # 3     3 mary  mary  mary  mary  mary  jane      1
    

    数据

    df <- structure(list(week = 1:3, Mon = c("jon", "jane", "mary"), Tues = c("jon", 
    "jane", "mary"), Weds = c("jon", "jane", "mary"), Thurs = c("jon", 
    "jane", "mary"), Fri = c("mary", "jane", "mary"), Sat = c("mary", 
    "jane", "jane")), class = "data.frame", row.names = c(NA, -3L))
    

    【讨论】:

    • 我使用了 colsums,非常完美!谢谢
    • 如果我只想检查选择变量(例如,仅周一、周三、周六)怎么办?编辑:nvm,从您的 dplyr 示例中可以清楚地看出它是如何工作的)
    • 实际上,当我尝试 df %>% rowwise() %>% mutate(flag = +any(c_across(Mon, Wed, Sat) %in% c("jon", "mary" ))) %>% ungroup() 我得到一个错误。这种方式不可以吗?
    • @M1245689 您需要将这些变量包围在c() 中,即c_across(c(Mon, Weds, Sat))。对于base 解决方案,只需将df[-1] 替换为df[c("Mon", "Weds", "Sat")] 即可。
    【解决方案2】:

    你可以使用rowSums

    df$flag <- +(rowSums(df[-1] == 'jon' | df[-1] == 'mary') > 0)
    
    #  week  Mon Tues Weds Thurs  Fri  Sat flag
    #1    1  jon  jon  jon   jon mary mary    1
    #2    2 jane jane jane  jane jane jane    0
    #3    3 mary mary mary  mary mary jane    1
    

    如果您要比较更多值并且无法单独编写每个值,则可以使用以下任何一种方法。

    more_values <- c('jon', 'mary')
    df$flag <- apply(df[-1], 1, function(x) as.integer(any(x %in% more_values)))
    df$flag <- +as.integer(rowSums(sapply(df[-1], `%in%`, more_values)) > 0)
    df$flag <- +(Reduce(`|`, lapply(df[-1], `%in%`, more_values)))
    

    【讨论】:

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