Вот одна идея. Мы можем рассчитать общую сумму каждой даты и затем построить общую сумму.
library(tidyverse)
library(lubridate)
dat2 <- dat %>%
# Convert to date class
mutate_at(vars(ends_with("time")), ymd) %>%
# Create a date sequence and expand it
mutate(Date = map2(start_time, end_time, seq.Date, by = 1)) %>%
unnest(cols = Date) %>%
# Calculate the total amount for each date
group_by(person, Date) %>%
summarize(amount = sum(amount))
ggplot(dat2, aes(x = Date, y = amount, color = person)) +
geom_point() +
geom_line()
Вот еще один вариант. Это тот же способ расширить фрейм данных на основе даты. После этого мы можем использовать stat_summary
для построения данных.
library(tidyverse)
library(lubridate)
dat2 <- dat %>%
# Convert to date class
mutate_at(vars(ends_with("time")), ymd) %>%
# Create a date sequence and expand it
mutate(Date = map2(start_time, end_time, seq.Date, by = 1)) %>%
unnest(cols = Date)
ggplot(dat2, aes(x = Date, y = amount, color = person)) +
stat_summary(fun.y = sum, geom = "path")
Обновление
Это решение добавляет 0 к следующей дате последней даты для каждого человека
library(tidyverse)
library(lubridate)
dat2 <- dat %>%
# Convert to date class
mutate_at(vars(ends_with("time")), ymd) %>%
# Create a date sequence and expand it
mutate(Date = map2(start_time, end_time, seq.Date, by = 1)) %>%
unnest(cols = Date) %>%
# Calculate the total amount for each date
group_by(person, Date) %>%
summarize(amount = sum(amount))
dat3 <- dat2 %>%
# Find the last date for each person
filter(Date == max(Date)) %>%
# Add one day to the last date for each person
# Set amount to be 0
mutate(Date = Date + 1, amount = 0)
# Combine data frames
dat4 <- bind_rows(dat2, dat3)
ggplot(dat4, aes(x = Date, y = amount, color = person)) +
geom_point() +
geom_line()
DATA
dat <- read.table(text = "person start_time end_time amount
A '2019-10-04' '2020-04-21' 10
A '2019-12-10' '2020-01-09' 20
B '2019-11-04' '2020-08-21' 30
B '2019-12-10' '2020-01-20' 15
C '2019-12-20' '2020-03-19' 5",
stringsAsFactors = FALSE, header = TRUE)