在 R 中创建矩阵时可以使用算术吗?

Can I use arithmetic when creating a matrix in R?

我需要一些帮助来创建矩阵。我有一个包含多个组的大型数据集。每组分为案例和非案例。

例如

Group Cases Noncases
GroupA 4 7
GroupB 9 4
GroupC 10 3

我想创建一个矩阵,将一组与其他组的总和进行比较。

例如:

Disease Category GroupA NotGroupA
Case 4 19
Noncase 7 7

目标是建立一个矩阵,让我可以 运行 卡方检验 and/or Fisher 精确检验(取决于样本量)。

我已尝试使用以下代码将数据框中的值外推到矩阵中:

GroupA <- as.table(matrix(c(df[1,3], df[1,4], (sum(df$group_cases)-df$group_cases[1])), (sum(df$Noncases)-df$Noncases[1])), nrow=2, ncol=2,
                dimnames=list(Group= c("A", "Other"),
                              Case = c(1, 0)))

但是,我收到以下错误:

Warning message:
In matrix(c(df[1, 3], df[1, 4], (sum(df$group_cases) -  :
  data length [3] is not a sub-multiple or multiple of the number of rows [329]

它输出一个 329 行的列表而不是一个 2 x 2 矩阵。

因为我有很多组,所以我希望R在构造矩阵时为我计算值。我不想单独计算“NotGroup_”列,因为这为人为错误留出了空间。

你们都建议如何构建这个矩阵,是否可以让 R 在创建矩阵时计算 columns/subtract 个值的总和?

感谢您的帮助!

设置示例:

dd <- data.frame(Group = LETTERS[1:3], Cases = c(4, 9, 10),
                 Noncases = c(7,4,3))

函数:

mktab <- function(focal, data) {
    ## subset rows according to whether $Group == focal or not
    ## subset cols according to "Cases"/"Noncases"
    ## sum() the not-focal elements
    matrix(c(data[data$Group==focal, "Cases"],
             sum(data[data$Group!=focal, "Cases"]),
             data[data$Group==focal, "Noncases"],
             sum(data[data$Group!=focal, "Noncases"])
             ),
           nrow = 2,
           byrow=TRUE,
           dimnames = list(c("Case", "Noncase"),
                           c(focal, paste0("not_", focal)))
           )
}

mktab("A", dd)
             

结果:

        A not_A
Case    4    19
Noncase 7     7

dplyr

library(dplyr)
library(tidyr) # pivot_*
dat %>%
  mutate(Group = ifelse(Group == "GroupA", "GroupA", "NotGroupA")) %>%
  pivot_longer(-Group, names_to = c("Case")) %>%
  pivot_wider(Case, names_from = Group, values_from = value, values_fn = list(value = sum))
# # A tibble: 2 x 3
#   Case     GroupA NotGroupA
#   <chr>     <int>     <int>
# 1 Cases         4        19
# 2 Noncases      7         7

基础 R

dat2 <- transform(dat, Group = ifelse(Group == "GroupA", "GroupA", "NotGroupA"))
aggregate(. ~ Group, data = dat2, FUN = sum)
#       Group Cases Noncases
# 1    GroupA     4        7
# 2 NotGroupA    19        7

(虽然轴是相反的)


数据

dat <- structure(list(Group = c("GroupA", "GroupB", "GroupC"), Cases = c(4L, 9L, 10L), Noncases = c(7L, 4L, 3L)), class = "data.frame", row.names = c(NA, -3L))

一个相关的link提供了很多“分组汇总”的方法:Calculate the mean by group