ggplot2: Creating Bar Plot for every element on x-axis but also for the whole sample

Viewed 153

I have a variable.A in a dataset:

variable.A = c('Dem', 'Rep', 'Ind', 'NA')

My objective: I want to plot the means from another variable (variable.X) for 1) 'Dem', 2) 'Rep' and 3) the whole sample (so 'Dem' + 'Rep' + 'Ind').

My first step is to filter out the 'NA' elements in variable.A:

new_dataset = dataset %>%
  filter(variable.A != 'NA')

Next, I create a bar plot for both variables using the ggplot command:

ggplot(new_dataset, aes(x=variable.A, y=variable.X)) + 
  stat_summary(aes(y = variable.X),
               fun = mean, na.rm = TRUE,
               geom = "bar",
               size = 3)

It plots the means for all three group elements. Here is an image of the plot output:

bar plot

My questions now are:

  1. How can I remove group element 'neutral' from the bar plot?
  2. How can I, in addition to plotting the mean for 'Dem' and 'Rep', create a third group in the bar plot (let's call it 'sample.mean'), that represents the mean to variable.X for the entire sample ('Dem' + 'Rep' + 'Ind')?

Thanks for any help!

2 Answers

Try this option (not tested as no data was shared). It can be better computing the summary values using dplyr with summarise(). If you want to add the sample mean you can use bind_rows(). The option limits in scale_x_discrete() allows setting the elements in the axis. Here the code:

library(ggplot2)
library(dplyr)
#Code
new_dataset %>%
  group_by(variable.A) %>%
  summarise(variable.X=mean(variable.X)) %>%
  bind_rows(new_dataset %>%
              summarise(variable.X=mean(variable.X)) %>%
              mutate(variable.A='Sample.Mean')) %>%
  ggplot(aes(x=variable.A, y=variable.X)) + 
  geom_bar(stat='identity')+
  scale_x_discrete(limits=c( 'Dem','Rep','Sample.Mean'))

Update: In order to add the confidence bars, you would need to compute the values for the bands as well as the entire sample in this way. I have used a dummy dataset for that goal:

#Keep randomness of simulated data
set.seed(123)
#Data
new_dataset <- data.frame(variable.A=sample(c('Dem','Rep'),50,replace = T),
                          variable.X=round(runif(50,1,10),0))
#Code
new_dataset %>%
  group_by(variable.A) %>%
  summarise(Mean=mean(variable.X),
            SD=sd(variable.X,na.rm=T),
            Low=Mean-qnorm(0.95)*SD,
            Upper=Mean+qnorm(0.95)*SD) %>%
  bind_rows(new_dataset %>%
              summarise(Mean=mean(variable.X),
                        SD=sd(variable.X,na.rm=T),
                        Low=Mean-qnorm(0.95)*SD,
                        Upper=Mean+qnorm(0.95)*SD) %>%
              mutate(variable.A='Sample.Mean')) %>%
  select(-SD) %>%
  ggplot(aes(x=variable.A, y=Mean)) + 
  geom_bar(stat='identity')+
  geom_errorbar(aes(ymin=Low,ymax=Upper),width=0.3)+
  scale_x_discrete(limits=c( 'Dem','Rep','Sample.Mean'))

Output:

enter image description here

We can do this in base R

df1 <- rbind(aggregate(variable.X ~ variable.A, new_dataset, mean),
       data.frame(variable.A = 'Sample.Mean', variable.X = mean(new_dataset$variable.X))

Then, use ggplot on the new dataset

library(ggplot2)
ggplot(df1, aes(x=variable.A, y=variable.X)) + 
     geom_bar(stat='identity')+
     scale_x_discrete(limits=c('Dem','Rep','Sample.Mean'))
Related