Могу ли я установить свободные масштабы для эстетики, отличной от x и y (например, размер) при использовании facet_grid? - PullRequest
0 голосов
/ 07 февраля 2019

facet_grid и facet_wrap имеют параметр scale , который, насколько мне известно, позволяет каждому графику корректировать масштабы оси x и / или y в соответствии с отображаемыми данными.Так как в соответствии с грамматикой ggplot x и y всего лишь два среди многих эстетик, и есть шкала для каждой эстетики, я подумал, что было бы разумно иметь возможность позволить каждой эстетике быть свободной, но пока я не нашелспособ сделать это.

Я пытался установить его, в частности, для размера, поскольку иногда переменные живут в разном порядке в зависимости от группы, которую я использую для фасета, и наличияОдна и та же шкала для каждой группы блокирует возможность увидеть изменения внутри группы.

Воспроизводимый пример:

set.seed(1)
x <- runif(20,0,1)
y <- runif(20,0,1)
groups <- c(rep('small', 10), rep('big', 10))
size_small <- runif(10,0,1)
size_big   <- runif(10,0,1) * 1000

df <- data.frame(x, y, groups, sizes = c(size_small, size_big))

И вспомогательная функция для построения графика:

basic_plot <- function(df) ggplot(df) + 
  geom_point(aes(x, y, size = sizes, color = groups)) + 
  scale_color_manual(values = c('big' = 'red', 'small' = 'blue')) +
  coord_cartesian(xlim=c(0,1), ylim=c(0,1))

Если я построим данные как есть, мы получим следующее:

basic_plot(df)

Не граненый участок

Синие точки относительно маленькие, но мы ничего не можемсможет сделать.Если мы добавим фасет:

basic_plot(df) +
  facet_grid(~groups, scales = 'free')

Граненый участок

Синие точки продолжают оставаться маленькими.Но я хотел бы воспользоваться тем фактом, что я делю данные на две части, и позволяю масштабам приспосабливаться к данным каждого графика.Я хотел бы иметь что-то вроде следующего:

plot_big <- basic_plot(df[df$groups == 'big',])
plot_small <- basic_plot(df[df$groups == 'small',])

grid.arrange(plot_big, plot_small, ncol = 2)

Что я хочу

Можно ли это сделать, не прибегая к такого рода микроуправлению или ручному масштабированиютаких размеров, как следующие?

df %>% 
  group_by(groups) %>% 
  mutate(maximo = max(sizes),
         sizes = scale(sizes, center = F)) %>% 
  basic_plot() +
  facet_grid(~groups)

Я могу справиться с этими задачами, я просто пытаюсь понять, не пропускаю ли я другой вариант, или я неправильно понимаю грамматику графики.

Спасибо, что уделили время!

1 Ответ

0 голосов
/ 07 февраля 2019

Как уже упоминалось, оригинальная сюжетная эстетика сохраняется при вызове facet_wrap.Поскольку вам нужны сгруппированные графики, рассмотрим base::by (функция фрейма данных поднабора), заключенную в do.call:

do.call(grid.arrange, 
        args=list(grobs=by(df, df$groups, basic_plot), 
                  ncol=2,
                  top="Grouped Point Plots"))

Grouped Plot Output


Если вам нужно поделиться легендой, я всегда использую эту обертку из @ ответа Стивена Локтона

do.call(grid_arrange_shared_legend, by(df, df$groups, basic_plot))

Shared Legend Plot Output

...