C# 计算datetime列表中的总分钟数
我有预约班的名单。 在下面的代码中C# 计算datetime列表中的总分钟数,c#,algorithm,C#,Algorithm,我有预约班的名单。 在下面的代码中 任命1、任命2和任命3是相交的 任命4和任命5是相交的 任命6是不相交的 任命1、任命2和任命3开始日期时间为“2018-07-10 08:00:00”,结束日期时间为“2018-07-10 12:00:00”,总时间为4小时 任命4和任命5开始日期时间为“2018-07-10 14:00:00”,结束日期时间为“2018-07-10 17:00:00”,总时间为3小时 任命6是不相交的,来这里1小时 总时间为4+3+1=8 如何在给定的约会日期时间值中找
- 任命1、任命2和任命3是相交的
- 任命4和任命5是相交的
- 任命6是不相交的
- 任命1、任命2和任命3开始日期时间为“2018-07-10 08:00:00”,结束日期时间为“2018-07-10 12:00:00”,总时间为4小时
- 任命4和任命5开始日期时间为“2018-07-10 14:00:00”,结束日期时间为“2018-07-10 17:00:00”,总时间为3小时
- 任命6是不相交的,来这里1小时
class Program
{
static void Main(string[] args)
{
List<Appointment> appointments = new List<Appointment>();
Appointment appointment1 = new Appointment();
appointment1.StartDate = new DateTime(2018, 07, 11, 08, 00, 00);
appointment1.FinishDate = new DateTime(2018, 07, 11, 11, 00, 00);
Appointment appointment2 = new Appointment();
appointment2.StartDate = new DateTime(2018, 07, 11, 10, 00, 00);
appointment2.FinishDate = new DateTime(2018, 07, 11, 12, 00, 00);
Appointment appointment3 = new Appointment();
appointment3.StartDate = new DateTime(2018, 07, 11, 09, 00, 00);
appointment3.FinishDate = new DateTime(2018, 07, 11, 12, 00, 00);
Appointment appointment4 = new Appointment();
appointment4.StartDate = new DateTime(2018, 07, 11, 14, 00, 00);
appointment4.FinishDate = new DateTime(2018, 07, 11, 16, 00, 00);
Appointment appointment5 = new Appointment();
appointment5.StartDate = new DateTime(2018, 07, 11, 15, 00, 00);
appointment5.FinishDate = new DateTime(2018, 07, 11, 17, 00, 00);
Appointment appointment6 = new Appointment();
appointment6.StartDate = new DateTime(2018, 07, 11, 18, 00, 00);
appointment6.FinishDate = new DateTime(2018, 07, 11, 19, 00, 00);
appointments.Add(appointment1);
appointments.Add(appointment2);
appointments.Add(appointment3);
appointments.Add(appointment4);
appointments.Add(appointment5);
appointments.Add(appointment6);
Console.ReadLine();
}
}
public class Appointment
{
public DateTime StartDate { get; set; }
public DateTime FinishDate { get; set; }
}
类程序
{
静态void Main(字符串[]参数)
{
列表约会=新列表();
预约1=新预约();
任命1.StartDate=新日期时间(2018,07,11,08,00,00);
任命1.FinishDate=新日期时间(2018,07,11,11,00,00);
约会约会2=新约会();
任命2.StartDate=新日期时间(2018,07,11,10,00,00);
任命2.FinishDate=新的日期时间(2018,07,11,12,00,00);
预约3=新预约();
任命3.StartDate=新日期时间(2018,07,11,09,00,00);
任命3.FinishDate=新的日期时间(2018,07,11,12,00,00);
预约4=新预约();
任命4.StartDate=新日期时间(2018,07,11,14,00,00);
任命4.FinishDate=新的日期时间(2018,07,11,16,00,00);
预约5=新预约();
任命5.StartDate=新日期时间(2018,07,11,15,00,00);
任命5.FinishDate=新的日期时间(2018,07,11,17,00,00);
预约6=新预约();
任命6.StartDate=新日期时间(2018,07,11,18,00,00);
任命6.FinishDate=新的日期时间(2018,07,11,19,00,00);
任命。添加(任命1);
任命。添加(任命2);
任命。添加(任命3);
任命。添加(任命4);
任命。添加(任命5);
任命。添加(任命6);
Console.ReadLine();
}
}
公开课任命
{
公共日期时间起始日期{get;set;}
public DateTime FinishDate{get;set;}
}
您知道TimeSpan类的属性吗
(dateA - dateB).TotalMinutes
您首先需要合并重叠时间,然后对时间跨度求和:
void Main()
{
List<Appointment> appointments = new List<Appointment>();
Appointment appointment1 = new Appointment();
appointment1.StartDate = new DateTime(2018, 07, 11, 08, 00, 00);
appointment1.FinishDate = new DateTime(2018, 07, 11, 11, 00, 00);
Appointment appointment2 = new Appointment();
appointment2.StartDate = new DateTime(2018, 07, 11, 10, 00, 00);
appointment2.FinishDate = new DateTime(2018, 07, 11, 12, 00, 00);
Appointment appointment3 = new Appointment();
appointment3.StartDate = new DateTime(2018, 07, 11, 09, 00, 00);
appointment3.FinishDate = new DateTime(2018, 07, 11, 12, 00, 00);
Appointment appointment4 = new Appointment();
appointment4.StartDate = new DateTime(2018, 07, 11, 14, 00, 00);
appointment4.FinishDate = new DateTime(2018, 07, 11, 16, 00, 00);
Appointment appointment5 = new Appointment();
appointment5.StartDate = new DateTime(2018, 07, 11, 15, 00, 00);
appointment5.FinishDate = new DateTime(2018, 07, 11, 17, 00, 00);
Appointment appointment6 = new Appointment();
appointment6.StartDate = new DateTime(2018, 07, 11, 18, 00, 00);
appointment6.FinishDate = new DateTime(2018, 07, 11, 19, 00, 00);
appointments.Add(appointment1);
appointments.Add(appointment2);
appointments.Add(appointment3);
appointments.Add(appointment4);
appointments.Add(appointment5);
appointments.Add(appointment6);
var ranges = appointments.Select(a => new Range {Start=a.StartDate, End=a.FinishDate});
var total = MergeTimes(ranges).Sum(a => (a.End-a.Start).TotalHours);
Console.WriteLine(total);
}
public class Appointment
{
public DateTime StartDate { get; set; }
public DateTime FinishDate { get; set; }
}
public class Range
{
public DateTime Start {get;set;}
public DateTime End {get;set;}
}
public IEnumerable<Range> MergeTimes(IEnumerable<Range> times)
{
if (times.Count() == 0)
{
return times;
}
Range[] orderedTimes = (from t in times
orderby t.Start
select t).ToArray();
List<Range> merged = new List<Range>();
Range current = new Range
{
Start = orderedTimes[0].Start,
End = orderedTimes[0].End
};
for (int i = 0; i < orderedTimes.Length; i++)
{
if (current.Start <= orderedTimes[i].End && current.End >= orderedTimes[i].Start)
{
current.Start = ((current.Start < orderedTimes[i].Start) ? current.Start : orderedTimes[i].Start);
current.End = ((current.End > orderedTimes[i].End) ? current.End : orderedTimes[i].End);
}
else
{
merged.Add(new Range
{
Start = current.Start,
End = current.End
});
current = new Range
{
Start = orderedTimes[i].Start,
End = orderedTimes[i].End
};
}
}
merged.Add(new Range
{
Start = current.Start,
End = current.End
});
return merged;
}
void Main()
{
列表约会=新列表();
预约1=新预约();
任命1.StartDate=新日期时间(2018,07,11,08,00,00);
任命1.FinishDate=新日期时间(2018,07,11,11,00,00);
约会约会2=新约会();
任命2.StartDate=新日期时间(2018,07,11,10,00,00);
任命2.FinishDate=新的日期时间(2018,07,11,12,00,00);
预约3=新预约();
任命3.StartDate=新日期时间(2018,07,11,09,00,00);
任命3.FinishDate=新的日期时间(2018,07,11,12,00,00);
预约4=新预约();
任命4.StartDate=新日期时间(2018,07,11,14,00,00);
任命4.FinishDate=新的日期时间(2018,07,11,16,00,00);
预约5=新预约();
任命5.StartDate=新日期时间(2018,07,11,15,00,00);
任命5.FinishDate=新的日期时间(2018,07,11,17,00,00);
预约6=新预约();
任命6.StartDate=新日期时间(2018,07,11,18,00,00);
任命6.FinishDate=新的日期时间(2018,07,11,19,00,00);
任命。添加(任命1);
任命。添加(任命2);
任命。添加(任命3);
任命。添加(任命4);
任命。添加(任命5);
任命。添加(任命6);
变量范围=约会。选择(a=>新范围{Start=a.StartDate,End=a.FinishDate});
var total=MergeTimes(ranges).Sum(a=>(a.End-a.Start).TotalHours);
控制台写入线(总计);
}
公开课任命
{
公共日期时间起始日期{get;set;}
public DateTime FinishDate{get;set;}
}
公共类范围
{
公共日期时间开始{get;set;}
公共日期时间结束{get;set;}
}
公共IEnumerable合并次数(IEnumerable times)
{
if(times.Count()==0)
{
返回次数;
}
范围[]orderedTimes=(从t开始,以时间为单位
orderby t.Start
选择t).ToArray();
列表合并=新列表();
量程电流=新量程
{
Start=orderedTimes[0]。开始,
End=orderedTimes[0]。结束
};
for(int i=0;iorderedTimes[i].End)?current.End:orderedTimes[i].End);
}
其他的
{
合并。添加(新范围)
{
开始=当前。开始,
结束=当前。结束
});
当前=新范围
{
Start=orderedTimes[i]。开始,
End=orderedTimes[i]。结束
};
}
}
合并。添加(新范围)
{
开始=当前。开始,
结束=当前。结束
});
返回合并;
}
解决这一问题的一种方法是收集约会所涵盖的时间,然后将其分组
您可以向应用程序添加一个方法
public IEnumerable<int> GetHours()
{
List<int> hours = new List<int>();
var startDate = StartDate;
var finishDate = FinishDate;
while(startDate < finishDate)
{
hours.Add(startDate.Hour);
startDate = startDate.AddHours(1);
}
return hours;
}
var result = appointments.SelectMany(a => a.GetHours()).GroupBy(i => i);
Console.WriteLine("Total hours: {0}", result.Count()); //This is the count
foreach (var hour in result)
{
Console.WriteLine("{0} => {1}", hour.Key, hour.Count());
}
Total hours: 8
8 => 1
9 => 2
10 => 3
11 => 2
14 => 1
15 => 2
16 => 1
18 => 1
var total = appointments
.OrderBy(appointment => appointment.StartDate)
.Aggregate(new Tuple<double, DateTime?>(0.0, null), (acc, item) => {
if (!acc.Item2.HasValue || acc.Item2.Value <= item.StartDate) // Disjoint
return new Tuple<double, DateTime?>(
acc.Item1 + (item.FinishDate - item.StartDate).TotalHours,
item.FinishDate);
else if (acc.Item2.Value >= item.FinishDate) // Include
return acc;
else // Partially overlap
return new Tuple<double, DateTime?>(
acc.Item1 + (item.FinishDate - acc.Item2.Value).TotalHours,
item.FinishDate);
})
.Item1;
// 8
Console.WriteLine(total);