Создать график с пробелами - PullRequest
1 голос
/ 17 октября 2019

Предположим, у нас есть график более 2 лет. Каждый год мы хотим что-то делать в определенные дни и отмечать эти дни на временной шкале. Похож на символ Ганта, но разница в том, что периоды могут иметь промежутки между ними. Это означает, например, что есть деятельность с 13 по 20. апреля, а следующая с 1 по 8. мая того же года. В приведенном ниже MWE я использую только период времени с 1 января 2000 года по 28 февраля 2000 года для простоты:

library(data.table)
library(ggplot2)
x <- seq(as.Date("2000/01/01"),
         as.Date("2000/02/28"), "day")
y <- x
y[c(3,6,8,9,34:43,50:59)] <- NA
x[c(1,2,3,12:33,44:58)] <- NA
timetable <- data.table(Year=c(rep("Year_1",59),rep("Year_2",59)),
date=c(x,y))

Как я могу создать расписание, которое иллюстрирует действия в форме прямоугольных фигур? Аналогично диаграммам, показанным здесь: Диаграммы Ганта с R или здесь: Создание многопроектной временной шкалы с использованием ggplot2 в R Но здесь это должно позволять промежутки между ними.

Другими словами, я пытаюсь заполнить существующий график и пропустить дни без каких-либо действий (пусто). Как это можно сделать с ggplot2?

1 Ответ

0 голосов
/ 17 октября 2019

Так что здесь есть возможность;сначала вы узнаете, какие из ваших дат являются пропущенными значениями, а затем длина цикла кодирует пропущенные значения:

is_missing <- timetable[, rle(is.na(date)), by = Year]

Исходя из этого, вы можете легко рассчитать позиции дат в вашей таблице, которые не пропущены:

end <- cumsum(is_missing$lengths)
start <- end - is_missing$lengths + 1

# Take now only the parts that are not missing
end <- end[!is_missing$values]
start <- start[!is_missing$values]

Из этого вы можете построить новый фрейм данных, содержащий даты начала и окончания периодов:

newdf <- data.frame(
  Year  = timetable$Year[start],
  start = timetable$date[start],
  end   = timetable$date[end]
)
newdf$y <- 1:nrow(newdf) # just a counter for visualisation

, который вы можете использовать для построения чего-то вроде следующего:

ggplot(newdf) +
  geom_rect(aes(xmin = start, xmax = end, 
                ymin = 0 + y,
                ymax = 1 + y, fill = Year))

enter image description here

Обратите внимание, что переменная Year на самом деле не означает год, поскольку сами даты охватывают только один год (2000 год), поэтому ярассматривал это как категориальную переменную. Кроме того, 3-я и 6-я записи в newdf представляют собой только один день, который отображается в виде прямоугольника нулевой ширины на графике, поскольку он начинается и заканчивается в одной и той же точке:

> newdf
    Year      start        end y
1 Year_1 2000-01-04 2000-01-11 1
2 Year_1 2000-02-03 2000-02-12 2
3 Year_1 2000-02-28 2000-02-28 3
4 Year_2 2000-01-01 2000-01-02 4
5 Year_2 2000-01-04 2000-01-05 5
6 Year_2 2000-01-07 2000-01-07 6
7 Year_2 2000-01-10 2000-02-02 7
8 Year_2 2000-02-13 2000-02-18 8

Вы можете сделатьxmax = end + 1 или xmin = start - 1 внутри функции aes(), если вы хотите, чтобы эти 1-дневные периоды появлялись.

РЕДАКТИРОВАТЬ: Для переменной Year на оси Y вы можете рассматривать их как числовые вgeom_rect()

ggplot(newdf) +
  geom_rect(aes(xmin = start, xmax = end, 
                ymin = -0.45 + as.numeric(Year),
                ymax = 0.45 + as.numeric(Year), fill = Year)) +
  scale_y_continuous(breaks = seq_len(nlevels(newdf$Year)),
                     labels = levels(newdf$Year))

enter image description here

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...