I have a list of objects which have StartAt
and EndAt
, properties of type DateTime
, representing the start and end times of a reading session. I want to calculate the total duration of reading for each day, considering that a reading session can span across two days. For example, if a reading session starts on May 1 at 11:00 PM and ends on May 2 at 1:30 AM, I want to count 1 hour of reading for May 1 and 1.5 hours of reading for May 2. How can I achieve this using LINQ in C#?
DateTime currentDate = DateTime.UtcNow;
DateTime previousDate = currentDate.AddDays(-1);
var result = readingSessions
.Where(x => x.StartAt.Date == currentDate.Date || x.StartAt.Date == previousDate.Date)
.GroupBy(x => x.StartAt.Date)
.Select(x => new
{
Date = x.Key,
Sum = TimeSpan.FromSeconds(x.Sum(y => (y.EndAt - y.StartAt).TotalSeconds))
})
.ToList();
public class ReadingSession
{
public DateTime StartAt {get;set;}
public DateTime EndAt {get;set;}
}
Details
StartAt | EndAt |
---|---|
2023-05-01 08:00:00 PM | 2023-05-01 09:00:00 PM |
2023-05-01 11:00:00 PM | 2023-05-02 01:30:00 AM |
How to calculate ?
Let's assume that we want to calculate the total reading duration for May 1st and May 2nd based on the given StartAt and EndAt times.
For the first row, the user started reading at 8:00 PM on May 1st and ended at 9:00 PM on the same day. Therefore, the total reading duration on May 1st is 1 hour.
For the second row, the user started reading at 11:00 PM on May 1st and ended at 1:30 AM on May 2nd. In this case, we need to split the reading duration into two parts: one for May 1st and one for May 2nd.
On May 1st, the user read from 11:00 PM to 11:59 PM, which is a total of 1 hour. On May 2nd, the user read from 12:00 AM to 1:30 AM, which is a total of 1.5 hours. Therefore, the total reading duration on May 1st is 1 hour and the total reading duration on May 2nd is 1.5 hours.
What should the result look like?
On May 1st, the reader started at 8:00 PM and ended at 9:00 PM, which gives us a duration of 1 hour. They also started reading at 11:00 PM and continued until 12:00 AM, which adds another hour, giving a total of 2 hours for May 1st.
On May 2nd, the reader started reading at 12:00 AM and ended at 1:30 AM, which gives us a duration of 1.5 hours.
Therefore, the total reading duration for May 1st is 2 hours and for May 2nd it is 1.5 hours.