【问题标题】:Complete case analysis in (long) dataset with repeated measurements通过重复测量在(长)数据集中完成案例分析
【发布时间】:2021-07-07 13:07:28
【问题描述】:

我有一个重复测量的数据集,它是长格式的。

我们正在使用完整的案例分析。我们的终点评估了变量从基线到第 3 个月、从基线到第 6 个月以及干预组和对照组之间的减少情况。

我需要每个 ID,包括基线和第 3 个月的数据或基线和第 6 个月的数据。但是,由于我的数据是长格式的 - 我不希望将其切换为宽格式 - 如果我只需使用例如drop_na() 可能我只是删除了一个时间点缺少数据的行,尽管如果该 ID 没有另一个时间点的数据,它也应该丢失。

在下面的示例中,应删除 id 423 和 id 143,因为它们仅具有基线信息。

有人知道如何解决这个问题吗?

非常感谢!

数据框结构:

a <- structure(list(id = c(778, 778, 101, 101, 101, 543, 543, 543, 
423, 315, 315, 315, 491, 491, 504, 504, 708, 708, 708, 714, 714, 
714, 408, 408, 418, 418, 279, 279, 279, 143), time = c(0, 6, 
0, 3, 6, 0, 3, 6, 0, 0, 3, 6, 0, 6, 0, 6, 0, 3, 6, 0, 3, 6, 0, 
3, 0, 6, 0, 3, 6, 0), group = c("control", "control", "intervention", 
"intervention", "intervention", "intervention", "intervention", 
"intervention", "intervention", "control", "control", "control", 
"control", "control", "intervention", "intervention", "control", 
"control", "control", "intervention", "intervention", "intervention", 
"control", "control", "control", "control", "control", "control", 
"control", "control"), var = c(46, 72, 90, 50, 73, 90, 96, 95, 
75, 50, 80, 66, 52, 70, 100, 84, 90, 96, 85, 88, 88, 92, 60, 
30, 95, 71, 86, 80, 91, 100)), row.names = c(NA, -30L), class = "data.frame")

> print(a)

【问题讨论】:

  • 如果你需要完整的 obs 并且你有 3 个时间点,是否也应该删除所有具有 2 个 obs 的 id?
  • 没有。但实际上,我需要 id 始终在基线时提供信息,而不仅仅是在两个后续时间点。不过,我的示例不包括这种情况。
  • 好的,我更新了我的答案以包含您的最后一点。代码应该保留每个有基线和至少一个后续时间点的人。
  • 谢谢!它确实有效!

标签: r


【解决方案1】:

使用dplyr 的一种方式。您可以按 id 分组,然后使用 n() 函数计数,最后过滤到有多个观察值的位置。

library(dplyr)

                                                                                                                                                 
a2 <- a |> 
      group_by(id) |> 
      mutate(obs = n()) |> 
      filter(obs > 1)

或者如果您不想创建另一个变量,您可以省略 mutate 语句。

a2 <- a |> 
      group_by(id) |> 
      filter(n() > 1)

如果您需要完整的观察并且他们需要所有时间点,只需更改过滤器语句。

a2 <- a |> 
      group_by(id) |> 
      filter(n() == 3)

这应该适用于纵向分析。下面我确保他们有一个基线和不止一个观察。因此,如果他们只有 3 个月和 6 个月,他们就会被放弃。不过,我需要更多数据来对此进行测试,因为您的数据中没有这种情况。

a2 <- a |> 
  group_by(id) |> 
  mutate(obs = n()) |> 
  filter(obs > 1 & any(time == 0))

【讨论】:

    【解决方案2】:

    如果我理解正确,基线是time = 0。您可以选择id 的观察值在time 处的值不是0。

    library(dplyr)
    
    a %>% group_by(id) %>% filter(any(time != 0)) %>% ungroup
    
    #     id  time group          var
    #   <dbl> <dbl> <chr>        <dbl>
    # 1   778     0 control         46
    # 2   778     6 control         72
    # 3   101     0 intervention    90
    # 4   101     3 intervention    50
    # 5   101     6 intervention    73
    # 6   543     0 intervention    90
    # 7   543     3 intervention    96
    # 8   543     6 intervention    95
    # 9   315     0 control         50
    #10   315     3 control         80
    # … with 18 more rows
    

    这里是对应的base R和data.table选项-

    #Base R
    subset(a, ave(time != 0, id, FUN = any))
    
    #data.table
    library(data.table)
    setDT(a)[, .SD[any(time != 0)], id]
    

    【讨论】:

      【解决方案3】:

      我们可能会使用

      library(dplyr)
      a %>%
          group_by(id) %>%
          filter(!all(time == 0)) %>%
          ungroup
      

      【讨论】:

        猜你喜欢
        • 2023-01-31
        • 1970-01-01
        • 2021-01-16
        • 2016-06-10
        • 2016-07-31
        • 2020-05-19
        • 1970-01-01
        • 2020-06-04
        • 2019-09-20
        相关资源
        最近更新 更多