R: Как агрегировать данные в проценты без пропуска данных для графика с накоплением в ggplot2?

Я хотел бы обобщить свои молекулярные данные «кариотипа» по местоположению и субстрату (см. Пример данных ниже) в процентах, чтобы создать график столбцов стека в ggplot2.

Я выяснил, как использовать «dcast», чтобы получить общее количество для каждого кариотипа, но не могу понять, как получить процент для каждого из трех кариотипов (то есть «BB», «BD», «DD»).

Данные должны быть в формате для создания гистограммы с накоплением в 'ggplot2'.

Пример данных:

library(reshape2)
Karotype.Data <- structure(list(Location = structure(c(1L, 1L, 1L, 1L, 1L, 1L, 
1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 1L, 2L, 2L, 
2L, 2L, 2L), .Label = c("Kampinge", "Kaseberga", "Molle", "Steninge"
), class = "factor"), Substrate = structure(c(1L, 1L, 1L, 1L, 
1L, 2L, 2L, 2L, 2L, 2L, 3L, 3L, 3L, 3L, 3L, 4L, 4L, 4L, 4L, 4L, 
2L, 2L, 2L, 2L, 2L), .Label = c("Kampinge", "Kaseberga", "Molle", 
"Steninge"), class = "factor"), Karyotype = structure(c(1L, 3L, 
4L, 4L, 3L, 3L, 4L, 4L, 4L, 3L, 1L, 4L, 3L, 4L, 4L, 3L, 1L, 4L, 
3L, 3L, 4L, 3L, 4L, 3L, 3L), .Label = c("", "BB", "BD", "DD"), class = "factor")), .Names = c("Location", 
"Substrate", "Karyotype"), row.names = c(135L, 136L, 137L, 138L, 
139L, 165L, 166L, 167L, 168L, 169L, 236L, 237L, 238L, 239L, 240L, 
326L, 327L, 328L, 329L, 330L, 426L, 427L, 428L, 429L, 430L), class = "data.frame")

## Summary count for each karoytype ##
Karyotype.Summary <- dcast(Karotype.Data , Location + Substrate ~ Karyotype, value.var="Karyotype", length)

person Keith W. Larson    schedule 16.03.2015    source источник
comment
Возможно, вам нужно сделать Karyotype.Summary[,3:5] <- Karyotype.Summary[,3:5]/rowSums(Karyotype.Summary[,3:5])*100   -  person Marat Talipov    schedule 16.03.2015


Ответы (2)


Вы можете использовать пакет dplyr:

library(dplyr)
z.counts <- Karotype.Data %>% 
  group_by(Location,Substrate,Karyotype) %>% 
  summarize(freq=n()) 

z.freq <- z.counts %>% 
  group_by(Location,Substrate) %>% 
  mutate(freq=freq/sum(freq)*100)

Здесь данные остаются в длинном формате, поэтому построить гистограмму с помощью ggplot несложно:

library(ggplot2)
ggplot(z.freq) + 
  aes(x=Karyotype,y=freq) + 
  facet_grid(Location~Substrate) + 
  geom_bar(stat='identity')

введите здесь описание изображения

person Marat Talipov    schedule 16.03.2015
comment
Я очень ценю вашу помощь, но есть два вопроса. Я не хочу включать данные с отсутствующими данными о кариотипе, а во-вторых, мне нужен график с накоплением столбцов. Тем не менее, если я теперь смогу понять, как удалить записи с отсутствующими данными о кариотипе, я думаю, что смогу построить правильные графики. Спасибо! - person Keith W. Larson; 16.03.2015

С некоторой помощью от «Марата Талипова» и многих других ответов на вопросы о Stackoverflow я обнаружил, что важно загружать «plyr» перед «dplyr» и использовать «summarise», а не «summarize». Затем удаление недостающих данных было последним шагом с использованием «фильтра».

library(dplyr)
z.counts <- Karotype.Data %>% 
  group_by(Location,Substrate,Karyotype) %>% 
  summarise(freq=n()) 

z.freq <- z.counts %>% filter(Karyotype != '') %>% 
  group_by(Location,Substrate) %>% 
  mutate(freq=freq/sum(freq))
z.freq

library (ggplot2)
ggplot(z.freq, aes(x=Substrate, y=freq, fill=Karyotype)) +
  geom_bar(stat="identity") +
  facet_wrap(~ Location)

Теперь я создал сюжет, который искал:

введите здесь описание изображения

person Keith W. Larson    schedule 16.03.2015