更快速地计算频率和从长到宽的方式

时间:2011-11-18 17:07:18

标签: r aggregate plyr reshape2

我试图获得两个变量的水平的每个组合的计数,“周”和“id”。我希望结果将“id”作为行,将“week”作为列,将计数作为值。

到目前为止我尝试过的示例(尝试过其他一些事情,包括添加虚拟变量= 1然后再添加fun.aggregate = sum):

library(plyr)
ddply(data, .(id), dcast, id ~ week, value_var = "id", 
        fun.aggregate = length, fill = 0, .parallel = TRUE)

但是,我必须做错事,因为这个功能没有完成。有更好的方法吗?

输入:

id      week
1       1
1       2
1       3
1       1
2       3

输出:

  1  2  3
1 2  1  1
2 0  0  1

4 个答案:

答案 0 :(得分:18)

您可以使用table命令:

table(data$id,data$week)

    1 2 3
  1 2 1 1
  2 0 0 1

如果“id”和“week”是数据框中的唯一列,则只需使用:

table(data)
#    week
# id  1 2 3
#   1 2 1 1
#   2 0 0 1

答案 1 :(得分:12)

您不需要ddply。来自dcast的{​​{1}}就足够了:

reshape2

修改:对于基本R解决方案(dat <- data.frame( id = c(rep(1, 4), 2), week = c(1:3, 1, 3) ) library(reshape2) dcast(dat, id~week, fun.aggregate=length) id 1 2 3 1 1 2 1 1 2 2 0 0 1 除外 - 由Joshua Uhlrich发布),请尝试table

xtabs

答案 2 :(得分:10)

ddply花费这么长时间的原因是按组拆分不是并行运行的(只是'拆分'上的计算),因此对于大量的组,它会很慢(和{ {1}})无济于事。

使用.parallel = Tdata.table::dcast版本&gt; = 1.9.2)的方法在时间和内存方面应该非常有效。在这种情况下,我们可以依赖默认参数值,只需使用:

data.table

或明确设置参数:

library(data.table) 
dcast(setDT(data), id ~ week)
# Using 'week' as value column. Use 'value.var' to override
# Aggregate function missing, defaulting to 'length'
#    id 1 2 3
# 1:  1 2 1 1
# 2:  2 0 0 1

对于dcast(setDT(data), id ~ week, value.var = "week", fun = length) # id 1 2 3 # 1: 1 2 1 1 # 2: 2 0 0 1 1.9.2之前的替代方案,请参阅修改。

答案 3 :(得分:1)

很少有tidyverse个选项:

library(tidyverse)

df %>%
  count(id, week) %>%
  spread(week, n, fill = 0)

#     id   `1`   `2`   `3`
#   <dbl> <dbl> <dbl> <dbl>
#1     1     2     1     1
#2     2     0     0     1

或分组,计算行数然后扩展

df %>%
  group_by(id, week) %>% #OR group_by_all()
  summarise(count = n()) %>%
  spread(week, count, fill = 0)