【问题标题】:R: Creating a new column based on existing conditions for first 150 rows only, and per participant?R:仅基于前 150 行和每个参与者的现有条件创建一个新列?
【发布时间】:2021-04-08 11:46:58
【问题描述】:

我有 50 位完成任务的参与者的数据。每个人完成了 450 次试验,这些试验分为 3 个区块(每个区块 150 次试验;这些是实验条件)。条件是“快乐”、“悲伤”和“中性”,并以随机顺序呈现给参与者。每个参与者数据当前都合并到一个整体数据框中,如下所示:

participant condition
1 neutral
1 neutral
1 neutral
(...) neutral
2 happy
2 happy
2 happy
(...) happy

我想创建一个名为 order 的新列,用于存储参与者完成的第一个条件块。因此,如果他们先完成中性块,则将其编码为 1,如果是快乐块,则将其编码为 2,如果是悲伤块,则将其编码为 3。

由于总共有 450 个试验,我只对前 150 个(第一个条件块)感兴趣,所以我尝试了以下代码:

dat %>% 
  group_by(participant) %>%
  slice(1:150) %>% 
  if(condition == "neutral"){
    dat$order <- 1
  } else if(condition == "happy"){
    dat$order <- 2
  } else if(condition == "sad"){
    dat$order <- 3
  }

但是,这会返回以下错误:条件的长度 > 1,并且只会使用第一个元素。谁能发现我哪里出错了?

【问题讨论】:

  • match(condition, c("neutral","happy","sad"))(在 mutate 内)将为您提供所需的整数,比 case_when 或几乎任何其他方法快得多(~30 倍)。
  • 每个参与者的输出应该有多少行,1、150、其他?

标签: r dplyr


【解决方案1】:

假设行按时间顺序排列,您可以使用group_by 分别处理每个参与者,summarize 为每个参与者获取一行,第一个条件,然后mutate 和case_when 映射文本值到编码值。

library(dplyr)

dat %>% 
    group_by(participant) %>%
    summarize(condition = first(condition)) %>%
    ungroup() %>%
    mutate(
        order = case_when(
            condition == "neutral" ~ 1, 
            condition == "happy" ~ 2, 
            condition == "sad" ~ 3
        )
    )

【讨论】:

    【解决方案2】:

    如果条件的所有 150 个值同时出现,您可以只检查每个参与者的 first 值而不是 150。

    library(dplyr)
    
    dat %>% 
      group_by(participant) %>%
      mutate(order = case_when(first(condition) == "neutral" ~ 1, 
                               first(condition) == "happy" ~ 2, 
                               first(condition) == "sad" ~ 3)) %>%
      ungroup
    

    【讨论】:

      【解决方案3】:

      如果没有我们可以使用的代表,很难知道,但有一个想法:

      dat %>% 
        group_by(participant) %>% 
        filter(row_number() <= 150) %>%
        mutate(order = case_when(
          condition == "neutral" ~ 1,
          condition == "happy" ~ 2,
          condition == "sad" ~ 3
          )
        )
      

      【讨论】:

        【解决方案4】:

        if() 未矢量化,当您要检查单个值时使用它。 ifelse() 或 dplyr::case_when() 是矢量化比较的好选择。您还遇到将整个数据框传递给if() 的问题。如果您尝试在dplyr 中创建新列,请使用mutate。我会建议

        dat %>% 
          group_by(participant) %>%
          slice(1:150) %>% 
          mutate(
            order = case_when(
              condition == "neutral" ~ 1,
              condition == "happy" ~ 2,
              condition == "sad" ~ 3
            )
          )
        

        【讨论】:

          猜你喜欢
          • 2015-03-31
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2019-11-18
          • 1970-01-01
          • 1970-01-01
          • 2021-11-05
          • 2019-04-20
          相关资源
          最近更新 更多