Подтвердить что ты не робот

Различные разрывы на грань гистограммы ggplot2

Требуется помощь латтисту, нуждающемуся в ggplot2: Какой синтаксис для запроса переменной per-facet разбивается на гистограмму?

library(ggplot2)
d = data.frame(x=c(rnorm(100,10,0.1),rnorm(100,20,0.1)),par=rep(letters[1:2],each=100))
# Note: breaks have different length by par
breaks = list(a=seq(9,11,by=0.1),b=seq(19,21,by=0.2))
ggplot(d, aes(x=x) ) + 
  geom_histogram() + ### Here the ~breaks should be added
  facet_wrap(~ par,  scales="free")

Как указано jucor, здесь еще несколько решения.

По специальному запросу и чтобы показать, почему я не являюсь отличным поклонником ggplot, версия lattice

library(lattice)
d = data.frame(x=c(rnorm(100,10,0.1),rnorm(100,20,0.1)),par=rep(letters[1:2],each=100))
# Note: breaks have different length by par
myBreaks = list(a=seq(8,12,by=0.1),b=seq(18,22,by=0.2))
histogram(~x|par,data=d,
          panel = function(x,breaks,...){
            # I don't know of a generic way to get the 
            # grouping variable with histogram, so 
            # this is not very generic
            par = levels(d$par)[which.packet()]
            breaks = myBreaks[[par]]
            panel.histogram(x,breaks=breaks,...)
          },
          breaks=NULL, # important to force per-panel compute
          scales=list(x=list(relation="free")))

enter image description here

4b9b3361

Ответ 1

Вот одна из альтернатив:

hls <- mapply(function(x, b) geom_histogram(data = x, breaks = b), 
              dlply(d, .(par)), myBreaks)
ggplot(d, aes(x=x)) + hls + facet_wrap(~par, scales = "free_x")

enter image description here

Если вам нужно уменьшить диапазон x, то

hls <- mapply(function(x, b) {
  rng <- range(x$x)
  bb <- c(rng[1], b[rng[1] <= b & b <= rng[2]], rng[2])
  geom_histogram(data = x, breaks = bb, colour = "white")
}, dlply(d, .(par)), myBreaks)

ggplot(d, aes(x=x)) + hls + facet_wrap(~par, scales = "free_x")

enter image description here

Ответ 2

Я не думаю, что можно дать разные точки разрыва в каждой грани.

В качестве обходного пути вы можете сделать два графика, а затем с помощью функции grid.arrange() из библиотеки gridExtra собрать их вместе. Чтобы установить точки останова в geom_histogram(), используйте binwidth= и установите одно значение для ширины ячейки.

p1<-ggplot(subset(d,par=="a"), aes(x=x) ) + 
  geom_histogram(binwidth=0.1) +
  facet_wrap(~ par)

p2<-ggplot(subset(d,par=="b"), aes(x=x) ) + 
  geom_histogram(binwidth=0.2) +
  facet_wrap(~ par)
library(gridExtra)
grid.arrange(p1,p2,ncol=2)

enter image description here

Ответ 3

Следуя примеру Didzis:

ggplot(dat=d, aes(x=x, y=..ncount..)) +
  geom_histogram(data = d[d$par == "a",], binwidth=0.1) +
  geom_histogram(data = d[d$par == "b",], binwidth=0.01) +  
  facet_grid(.~ par, scales="free")

EDIT: это работает для большего количества уровней, но, конечно, уже есть более совершенные решения.

# More facets
d <- data.frame(x=c(rnorm(200,10,0.1),rnorm(200,20,0.1)),par=rep(letters[1:4],each=100))

# vector of binwidths same length as number of facets - need a nicer way to calculate these
my.width=c(0.5,0.25,0.1,0.01)

out<-lapply(1:length(my.width),function(.i) data.frame(par=levels(d$par)[.i],ggplot2:::bin(d$x[d$par==levels(d$par)[.i]],binwidth=my.width[.i])))

my.df<-do.call(rbind , out)

ggplot(my.df) + geom_histogram(aes(x, y = density, width = width), stat =  "identity") + facet_wrap(~par,scales="free")

from https://groups.google.com/forum/?fromgroups=#!searchin/ggplot2/bin $20histogram $20by $20facet/ggplot2/xlqRIFPP-zE/CgfigIkgAAkJ

Ответ 4

Нельзя, строго говоря, давать разные разрывы в разных гранях. Но вы можете получить тот же эффект, создав другой слой для каждого аспекта (так же, как в user20650 answer), но в основном автоматизируя несколько вызовов geom_histogram:

d <- data.frame(x=c(rnorm(100,10,0.1),rnorm(100,20,0.1)),
                par=rep(letters[1:2],each=100))
breaks <- list(a=seq(9,11,by=0.1),b=seq(19,21,by=0.2))

ggplot(d, aes(x=x)) +
  mapply(function(d, b) {geom_histogram(data=d, breaks=b)}, 
         split(d, d$par), breaks) +
  facet_wrap(~ par,  scales="free_x")

enter image description here

Вызов mapply создает список geom_histogram, который можно добавить в график. Сложная часть состоит в том, что вам нужно вручную разделить данные (split(d, d$par)) на данные, которые входят в каждую грань.

Ответ 5

Загрузка библиотек

library(purrr)
library(gridExtra)

данные

d <- data.frame(x=c(rnorm(100,10,0.1),rnorm(100,20,0.1)),
                par=rep(letters[1:2],each=100))

разрывы

breaks <- list(a=seq(9,11,by=0.1),b=seq(19,21,by=0.2))

получить список ggplot

a1 <- map2(.x = split(d, d$par),
           .y = breaks, 
           .f = ~ {ggplot(.x, aes(x = x)) + geom_histogram(breaks = .y) + ylim(0,55) + facet_wrap(~ par, scales = "free_x")})

гистограммы сюжета

do.call("grid.arrange", c(a1, ncol = 2))

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