7

我有一个看起来像这样的数据框:

structure(list(ab = c(0, 1, 1, 1, 1, 0, 0, 0, 1, 1), bc = c(1, 
1, 1, 1, 0, 0, 0, 1, 0, 1), de = c(0, 0, 1, 1, 1, 0, 1, 1, 0, 
1), cl = c(1, 2, 3, 1, 2, 3, 1, 2, 3, 2)), .Names = c("ab", "bc", 
"de", "cl"), row.names = c(NA, -10L), class = "data.frame")

列 cl 表示集群关联,变量 ab,bc 和 de 携带二进制答案,其中 1 表示是,0 - 否。

我正在尝试创建一个表交叉表集群以及数据框中的所有其他列,即 ab、bc 和 de,其中集群成为列变量。想要的输出是这样的

    1  2  3
 ab 1  3  2
 bc 2  3  1
 de 2  3  1

我尝试了以下代码:

with(newdf, tapply(newdf[,c(3)], cl, sum))

这为我提供了一次只交叉制表一列的值。我的数据框有 1600 多列和 1 个簇列。有人可以帮忙吗?

4

5 回答 5

7

baseR 中:

t(sapply(data[,1:3],function(x) tapply(x,data[,4],sum)))
#   1 2 3
#ab 1 3 2
#bc 2 3 1
#de 2 3 1
于 2015-10-31T19:29:14.523 回答
7

一种使用dplyr方法是:

library(dplyr)
df %>% 
  #group by the varialbe cl
  group_by(cl) %>%
  #sum every column
  summarize_each(funs(sum)) %>%
  #select the three needed columns
  select(ab, bc, de) %>%
  #transpose the df
  t

输出:

   [,1] [,2] [,3]
ab    1    3    2
bc    2    3    1
de    2    3    1
于 2015-10-31T19:23:53.803 回答
6

您的数据采用半长半宽格式,并且您希望它采用全宽格式。如果我们首先将其转换为完整的长格式,这是最简单的:

library(reshape2)
df_long = melt(df, id.vars = "cl")
head(df_long)
#    cl variable value
# 1   1       ab     0
# 2   2       ab     1
# 3   3       ab     1
# 4   1       ab     1
# 5   2       ab     1
# 6   3       ab     0

然后我们可以将其转换为宽格式,sum用作聚合函数:

dcast(df_long, variable ~ cl, fun.aggregate = sum)
#   variable 1 2 3
# 1       ab 1 3 2
# 2       bc 2 3 1
# 3       de 2 3 1
于 2015-10-31T19:24:04.973 回答
2

您还可以组合tidyr:gatherreshape2::meltxtabs拥有您的列联表

library(tidyr)
xtabs(value ~ key + cl, data = gather(df, key, value, -cl))
##     cl
## key  1 2 3
##   ab 1 3 2
##   bc 2 3 1
##   de 2 3 1

如果您更喜欢使用管道

df %>%
  gather(key, value, -cl) %>%
  xtabs(value ~ key + cl, data = .)
于 2015-10-31T19:37:12.973 回答
0

只是为了更新使用 dplyr 的 pivot_longer (取代收集)遵循代码 dickoa 写道:

library(dplyr)

df %>% 
pivot_longer(cols = ab:de,
          names_to = "key",
          values_to = "value") %>% 
xtabs(value ~ key + cl, data = .)
于 2020-07-15T15:41:22.763 回答