8
ID <- 1:10 
group <- c(1,1,1,2,2,2,3,3,3,3)
var1 <- c(6:15) 
var2 <- c(7:16) 
var3 <- c(6:11, NA, NA, NA, NA)
var4 <- c(4:9, NA, NA, NA, NA) 
data <- data.frame(ID, group, var1, var2, var3, var4)

library(dplyr)
 data %>% group_by(group) %>% boxplot(var1, var2)

The last line does not work as i wish. The idea is to get 4 boxplots in one graphic. Two for each variable. Maybe i need to use ggplot2?

2
  • 4
    You mean like boxplot(value~group+variable, reshape2::melt(data, 1:2)) (May need install.packages("reshape2") beforehand)? Commented May 9, 2016 at 12:55
  • 2
    Possible duplicate of Plot multiple boxplot in one graph Commented May 9, 2016 at 13:32

3 Answers 3

13

You need to reorganize the data if you want to get both variables in the same plot. Here is a ggplot2 solution:

# load library
  library(ggplot2)
  library(tidyr)
  library(ggthemes)


# reorganize data
  df <- gather(data, "ID","group") 

#rename columns 
  colnames(df) <- c("ID","group","var","value")

# plot
  ggplot(data=df) + 
    geom_boxplot( aes(x=factor(group), y=value, fill=factor(var)), position=position_dodge(1)) +
    scale_x_discrete(breaks=c(1, 2, 3), labels=c("A", "B", "C")) +
    theme_minimal() +
    scale_fill_grey() 

enter image description here

Making boxplots with the same width is a whole different question (solution here), but one simple alternative would be like this:

# recode column `group` in the `data.frame`.
  df <- transform(df, group = ifelse(group==1, 'A', ifelse(group==2, 'B', "C")))

# plot
  ggplot(data=df) + 
  geom_boxplot( aes(x=factor(var), y=value, fill=factor((var))), position=position_dodge(1)) +
  geom_jitter(aes(x=factor(var), y=value, color=factor((var)))) +
  facet_grid(.~group, scales = "free_x") +
  theme_minimal()+
  scale_fill_grey() +
  theme(axis.text.x=element_blank(),
        axis.title.x=element_blank(),
        axis.ticks=element_blank())

enter image description here

Sign up to request clarification or add additional context in comments.

6 Comments

Thank you for this easy solution. I still have some "style" questions, because my actual dataset is a little bit more complicated.
ID <- 1:10 group <- c(1,1,1,2,2,2,3,3,3,3) var1 <- c(6:15) var2 <- c(7:16) var3 <- c(6:11, NA, NA, NA, NA) var4 <- c(4:9, NA, NA, NA, NA) data <- data.frame(ID, group, var1, var2, var3, var4) # load library library(ggplot2) library(tidyr) # reorganize data df <- gather(data, "ID","group") #rename columns colnames(df) <- c("ID","group","var","value") # plot ggplot(data=df) + geom_boxplot( aes(x=factor(group), y=value, fill=factor(var))) + geom_jitter(aes(x=factor(group), y=value))
# set space between the boxes, they are to close together, especially for the jitter # set all boxes the same width; Because of missings the third block is different # change colour to greyscales or black and white pattern # name the groups (1,2,3) --> "A","B","C"
Here you will find a solution for how to make boxplots with the same width. I've addressed your other points in the edit to my question
Thanks, this looks very nice :) When i add geom_jitter unfurtunately the dots are outside the boxes and i can not find a solution to change that. I tried to set width or as in your example position=position_dodge. Width does not change anything. Position made it one line in between.
|
5

You might try melting the data frame (mentioned in comment by @lukeA) first and then sticking to base graphics. ggplot2 or lattice are other good options.

library(reshape2)

DF <- melt(data, id.vars = c("ID", "group"), measure.vars = c("var1", "var2"))

boxplot(value ~ group + variable, DF)

enter image description here

Alternate lattice code, also using DF:

bwplot(~ value | variable + group, data = DF)

Alternate ggplot2 code, also using DF:

ggplot(DF, aes(x = factor(group), y = value, fill = variable)) + geom_boxplot()

Comments

0

Although quite late, a found a great base-R solution here

# Create some data, e.g. from https://en.wikipedia.org/wiki/One-way_analysis_of_variance#Example
df <- as.data.frame(matrix(c(6, 8, 13, 8, 12, 9, 4, 9, 11, 5, 11, 8, 3, 6, 7, 4, 8, 12),ncol = 3, byrow = TRUE))
df <- reshape(data = df, direction = "long", idvar=1:3, varying=1:3, sep = "", timevar = "Treatment")
df$Treatment <- as.factor(df$Treatment)
rownames(df) <- NULL

par(mfrow = c(2, 1))
par(mar=c(1,4,4,2) + 0.1) # mar=c(b,l,t,r)
boxplot(V ~ Treatment, data = df, xlab = NULL, xaxt = "n",
        ylab = "V", main = "One-way anova with 3 different levels of one factor")
stripchart(V ~ Treatment,     # Points
           data = df,         # Data
           method = "jitter", # Random noise
           pch = 19,          # Pch symbols
           col = 4,           # Color of the symbol
           vertical = TRUE,   # Vertical mode
           add = TRUE)        # Add it over

par(mar=c(5,4,0,2) + 0.1)
boxplot(V ~ Treatment, data = df, xlab = "Treatment",
        ylab = "V", main = NULL)
stripchart(V ~ Treatment,     # Points
           data = df,         # Data
           method = "overplot", # Random noise
           pch = 19,          # Pch symbols
           col = 4,           # Color of the symbol
           vertical = TRUE,   # Vertical mode
           add = TRUE)        # Add it over
par(mfrow = c(1, 1))

Result: enter image description here

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.