2012-06-04 21 views
6

我想要一个这样的情节,除了每个方面总和为100%。此时组M为0.05 + 0.25 = 0.30而不是0.20 + 0.80 = 1.00。ggplot:两组的相对频率

df <- rbind(
    data.frame(gender=c(rep('M',5)), outcome=c(rep('1',4),'0')), 
    data.frame(gender=c(rep('F',10)), outcome=c(rep('1',7),rep('0',3))) 
) 

df 

ggplot(df, aes(outcome)) + 
    geom_bar(aes(y = (..count..)/sum(..count..))) + 
    facet_wrap(~gender, nrow=2, ncol=1) 

(使用Y = ..density ..给出更坏的结果。)

+0

这里提供的答案是正确的方法。 ..density ..方法提供了许多其他答案, http://stackoverflow.com/questions/10064080/plot-relative-frequencies-with-dodged-bar-plots-in-ggplot2,http:// stackoverflow。 com/questions/17368223/ggplot2-multi-group-histogram-with-in-group-proportionortions-even-frequency,http://stackoverflow.com/questions/3695497/ggplot-showing-instead-of-counts-分类变量图表产生不同程度不正确的值。 – russellpierce

回答

9

我通常通过简单地预先计算的值的GGPLOT2外部,并使用stat = "identity"做到这一点:

df1 <- melt(ddply(df,.(gender),function(x){prop.table(table(x$outcome))}),id.vars = 1) 

ggplot(df1, aes(x = variable,y = value)) + 
    facet_wrap(~gender, nrow=2, ncol=1) + 
    geom_bar(stat = "identity") 
+0

这是正确的。我希望得到一个更简单的答案,看起来像是一种相对常见的图表。 :) – Andrew

+0

@andrew - 我这样做*很多*。制作自己的'geom'相对容易,这对于ggplot2的内置工具来说是一个很好的补充。 – Chase

+0

@Chase我可能是错误的,但我认为它不仅仅是一个新的geom,因为(我认为)美学被映射到变量之前。所以我认为这可能是一个设计功能方式上游的几何。 – joran

16

这是另一种方式

ggplot(df, aes(outcome)) + 
    geom_bar(aes(y = ..count../sapply(PANEL, FUN=function(x) sum(count[PANEL == x])))) + 
    facet_wrap(~gender, nrow=2, ncol=1) 
+1

多么可爱的黑客! – joran

+0

我喜欢这是短暂的,但是当我尝试从facet切换到position = dodge时,所有组的高度总和为100%(而不是在组内) – Andrew

+0

我希望我可以多加注意。 – Eduardo