using System.Collections.Generic;
public string Name { get; set; }
public DateTime Start { get; set; }
public DateTime End { get; set; }
private static IEnumerable<(TItem left, TItem right)> MyGroups<TSource, TItem>(
IEnumerable<TSource> source,
Func<TSource, TItem> start,
Func<TSource, TItem> stop,
IComparer<TItem> comparer = default) {
comparer = comparer ?? Comparer<TItem>.Default;
.Where(item => comparer.Compare(start(item), stop(item)) <= 0)
.OrderBy(item => start(item));
foreach (var item in ordered) {
var currentLeft = start(item);
var currentRight = stop(item);
else if (comparer.Compare(right, currentLeft) >= 0) {
right = comparer.Compare(right, currentRight) >= 0 ? right : currentRight;
yield return (left, right);
yield return (left, right);
public static void Main() {
var records = new List<Record> {
new Record { Name = "Group1 - A", Start = new DateTime(2024, 1, 1, 9, 0, 0), End = new DateTime(2024, 1, 1, 10, 0, 0) },
new Record { Name = "Group1 - B", Start = new DateTime(2024, 1, 1, 9, 30, 0), End = new DateTime(2024, 1, 1, 11, 0, 0) },
new Record { Name = "Group1 - C", Start = new DateTime(2024, 1, 1, 10, 30, 0), End = new DateTime(2024, 1, 1, 12, 0, 0) },
new Record { Name = "Group2 - D", Start = new DateTime(2024, 1, 1, 13, 0, 0), End = new DateTime(2024, 1, 1, 15, 0, 0) },
new Record { Name = "Group3 - E", Start = new DateTime(2024, 1, 2, 22, 0, 0), End = new DateTime(2024, 1, 2, 23, 0, 0) },
new Record { Name = "Group3 - F", Start = new DateTime(2024, 1, 2, 22, 30, 0), End = new DateTime(2024, 1, 3, 5, 0, 0) }
var result = MyGroups(records, rec => rec.Start, rec => rec.End);
var report = string.Join(Environment.NewLine, result
.Select((item, index) => $"Group {index + 1} - Start: {item.left:d/M/yyyy htt}, End: {item.right:d/M/yyyy htt}"));
Console.WriteLine(report);