我有以下数据框:
df <- read.table(text = "group age status
A 25 yes
A 32 no
A 58 yes
A 78 no
A 76 yes
B 21 no
B 71 yes
B 43 no
B 48 no
C 39 no
C 82 yes
C 87 no
C 91 yes", header = T)
我想对列进行分组,然后以某种方式进行汇总,如果年龄小于 50 岁并且状态为"is",则对这些值进行计数,然后计算年龄小于 50 岁的值的总数。 因此对于数据框中的“A”:
age_lt_50_yes = 1
age_lt_50 = 2
同样,对于年龄大于 50 岁,选择"is",然后选择年龄大于 50 岁; 为一个';这将是:
age_gt_50_yes = 2
age_gt_50 = 3
我实际上想要一个age_lt_50_yes/age_lt_50的比率,对于“A”来说,这个比率是1/2,对于“A”来说,age_gt_50_yes/age_gt_50 = 2/3
如果我遇到这样的情况 0/0;然后只想要 0 作为输出。
如何使用 dplyr 执行此操作?
这是我尝试过的:
df %>%
group_by(group) %>%
summarize(age_le50_prop = sum(age <= 50) / n(),
age_gt50_prop = sum(age > 50) / n())
我需要在摘要功能中添加状态
我的输出应该是这样的:
group_by age_lt_50 age_gr_50
A 0.5 0.66
B 0 1
C 0 0.66
最佳答案
您可以使用reframe()
,并简单地定义您需要的计数。最后一行将处理 0/0 的情况
reframe(
df,
age_lt_50 = sum(age<50 & status=="yes")/sum(age<50),
age_gt_50 = sum(age>=50 & status=="yes")/sum(age>=50),
.by=group) %>% replace(is.na(.),0)
输出:
group age_lt_50 age_gt_50
1 A 0.5 0.6666667
2 B 0.0 1.0000000
3 C 0.0 0.6666667
这里是一个替代方案,演示了使用 summarize()
而不是重新构造,并且(独立地)还演示了另一种检查分母中 0 可能性的方法:
df %>%
group_by(group) %>%
summarize(
age_lt_50 = {if(sum(age<50)==0) 0 else sum(age<50 & status=="yes")/sum(age<50)},
age_gt_50 = {if(sum(age>=50)==0) 0 else sum(age>=50 & status=="yes")/sum(age>=50)}
)
关于r - 用 dplyr 和条件总结,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/76184153/