首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >一组与多组的t检验

一组与多组的t检验
EN

Stack Overflow用户
提问于 2020-04-06 15:47:41
回答 4查看 59关注 0票数 2

我有下面的泰伯

代码语言:javascript
运行
复制
test_tbl <- tibble(name = rep(c("John", "Allan", "George", "Peter", "Paul"), each = 12),
                   category = rep(rep(LETTERS[1:4], each = 3), 5),
                   replicate = rep(1:3, 20),
                   value = sample.int(n = 1e5, size = 60, replace = T))


# A tibble: 60 x 4
   name  category replicate value
   <chr> <chr>        <int> <int>
 1 John  A                1 71257
 2 John  A                2 98887
 3 John  A                3 87354
 4 John  B                1 25352
 5 John  B                2 69913
 6 John  B                3 43086
 7 John  C                1 24957
 8 John  C                2 33928
 9 John  C                3 79854
10 John  D                1 32842
11 John  D                2 19156
12 John  D                3 50283
13 Allan A                1 98188
14 Allan A                2 26208
15 Allan A                3 69329
16 Allan B                1 32696
17 Allan B                2 81240
18 Allan B                3 54689
19 Allan C                1 77044
20 Allan C                2 97776
# … with 40 more rows

我想要group_by(name, category)并执行三个t.test调用,比较category B、C和D与category A。

我想从输出中存储estimatep.value。预期的结果如下:

代码语言:javascript
运行
复制
# A tibble: 5 x 7
  name   B_vs_A_estimate B_vs_A_p_value C_vs_A_estimate C_vs_A_p_value D_vs_A_estimate D_vs_A_p_value
  <chr>            <dbl>          <dbl>           <dbl>          <dbl>           <dbl>          <dbl>
1 John            -0.578         0.486            0.198          0.309           0.631         0.171 
2 Allan            0.140         0.644            0.728          0.283           0.980         0.485 
3 George          -0.778         0.320           -0.424          0.391          -0.154         0.589 
4 Peter           -0.435         0.470           -0.156          0.722           0.315         0.0140
5 Paul             0.590         0.0150          -0.473          0.475           0.681         0.407

我更喜欢使用tidyverse和/或broom的解决方案。

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2020-04-06 16:50:51

实现所需输出的方法有很多种,但也许这一种更直观,更易于调试(您可以将browser()放在任何地方)。

代码语言:javascript
运行
复制
test_tbl %>%
  group_by(name) %>%
  do({
    sub_tbl <- .
    expand.grid(g1="A", g2=c("B", "C", "D"), stringsAsFactors = FALSE) %>%
      mutate(test=as.character(glue::glue("{g1}_vs_{g2}"))) %>%
      rowwise() %>%
      do({
        gs <- .
        t_res <- t.test(sub_tbl %>% filter(category == gs$g1) %>% pull(value), 
                        sub_tbl %>% filter(category == gs$g2) %>% pull(value))
        data.frame(test=gs$test, estimate=t_res$statistic, p_value=t_res$p.value, 
                   stringsAsFactors = FALSE)
      })
  }) %>%
  ungroup() %>%
  gather(key="statistic", value="val", -name, -test) %>%
  mutate(test_statistic = paste(test, statistic, sep = "_")) %>%
  select(-test, -statistic) %>%
  spread(key="test_statistic", value="val")

结果

代码语言:javascript
运行
复制
# A tibble: 5 x 7
  name   A_vs_B_estimate A_vs_B_p_value A_vs_C_estimate A_vs_C_p_value A_vs_D_estimate A_vs_D_p_value
  <chr>            <dbl>          <dbl>           <dbl>          <dbl>           <dbl>          <dbl>
1 Allan           -0.270          0.803         -1.03            0.396           1.55           0.250
2 George           0.201          0.855          0.221           0.838           1.07           0.380
3 John            -1.59           0.249          0.0218          0.984          -0.410          0.704
4 Paul             0.116          0.918         -1.62            0.215          -1.53           0.212
5 Peter            0.471          0.664          0.551           0.611           0.466          0.680

它将记录按名称分组,然后应用一个函数(do #1)。在sub_tbl中保存子数据,展开所有测试用例(expand.grid),并使用两个字母组合创建一个test名称。现在,对于每个组合,应用函数来运行t-test (do #2)。该匿名函数在组1 (g1)和组2 (g2)之间执行测试,并返回带有结果的数据。第二部分主要是对列进行重新排列,以获得最终的输出。

票数 1
EN

Stack Overflow用户

发布于 2020-04-06 16:16:41

编辑:清洁代码

代码语言:javascript
运行
复制
map(unique(test_tbl$name),function(nm){test_tbl %>% filter(name == nm)}) %>% 
  map2(unique(test_tbl$name),function(dat,nm){
    map(LETTERS[2:4],function(cat){
      dat %>% 
        filter(category == "A") %>%
        pull %>% 
        t.test(dat %>% filter(category == cat) %>% pull)
    }) %>%
      map_dfr(broom::glance) %>% 
      select(statistic,p.value) %>% 
      mutate(
        name = nm,
        cross_cat = paste0(LETTERS[2:4]," versus A")
      )
  }) %>%
  {do.call(rbind,.)}
票数 0
EN

Stack Overflow用户

发布于 2020-04-06 16:36:38

代码语言:javascript
运行
复制
test_tbl %>%
  dplyr::group_by(name) %>%
  dplyr::summarise(estimate_AB = 
    t.test(value[category == "A"| category == "B"] ~ category[category == "A" | category == "B"]) %>% (function(x){x$estimate[1] - x$estimate[2]}), 
    pvalue_AB = t.test(value[category == "A"| category == "B"] ~ category[category == "A" | category == "B"]) %>% (function(x){x$p.value})
  )

以下是我按组测试A对B的方法。我认为您可以扩展我的方法,或者尝试从第一个解决方案中合并代码。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/61063661

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档