我需要计算两个日期之间的工作日数。工作日是周一至周五的任何一天,节假日除外。下面的代码执行此操作,但它使用循环。有没有人看到摆脱循环或至少优化它的方法?
感谢 康斯坦丁
using System;
using System.Linq;
namespace consapp
{
static class Program
{
static void Main(string[] args)
{
var holidays = new DateTime[] { new DateTime(2010, 11, 23), new DateTime(2010, 11, 30) };
var date_start = new DateTime(2010, 12, 3);
var date_end = date_start.AddDays(-9.9);
var duration = (date_end - date_start).Duration();
for (var d = date_end; d < date_start; d = d.Date.AddDays(1))
{
if (holidays.Contains(d.Date) || d.DayOfWeek == DayOfWeek.Saturday || d.DayOfWeek == DayOfWeek.Sunday)
{
duration -= TimeSpan.FromDays(1) - d.TimeOfDay;
}
}
Console.WriteLine(duration);
}
}
}
答案 0 :(得分:0)
这里的表现真的有问题吗?除非分析表明否则我猜这段代码并没有真正减慢你的应用程序。除非你计算每秒数千个长间隔的工作日,否则它的性能应该没问题。
如果您的假期列表比两个日期大得多,则将其转换为HashSet<T>
,其中包含O(1)查找时间。
当然,你可以扭转代码。因此,您不要在间隔期间循环,而是在假日期间。然后你只计算一个区间的工作日数(应该是简单的数学运算)并减去一周工作日的假日数。
如果确实有必要,您可以预先计算自某个固定日期以来的工作日,然后从该期间结束时的查找结果中减去该期间开头的查找结果。
答案 1 :(得分:0)
我会研究如下算法。 (对不起,没有提供代码。)
玩得开心!
编辑:有关源代码,请查看以下答案:Calculate the number of business days between two dates?
答案 2 :(得分:0)
如果您想要更快的代码,请不要在范围内的每一天循环:
从假日列表中删除星期日或星期六的所有假期,然后使用时间跨度方法为您提供两个日期之间的天数。通过一点点数学(考虑整数除以7),您可以得到该范围内的星期四天数,减去周末不会从该数字开始的假期数量,并且您已完成。
答案 3 :(得分:0)
按原样滚动。这不会浪费太多时间,因为边界很小。当你有一些工作代码时,继续前进。无需无理无故地优化代码。
答案 4 :(得分:0)
因为我把它作为一个有趣的谜题开始,这里是代码:
[Test]
public void TestDateTime() {
var start = DateTime.Now.Date;
var end = DateTime.Now.Date.AddDays(35);
var workdays = (end - start).Days - ((end - start).Days/7)*2
- (((end - start).Days%7==0)?0:(((int)start.DayOfWeek==0)?1:Math.Max(Math.Min((int)start.DayOfWeek + (end - start).Days%7 - 6, 2), 0)));
new []{DateTime.Now.AddDays(19), DateTime.Now.AddDays(20)}.ToList().ForEach(
x => { if (x.DayOfWeek != DayOfWeek.Saturday && x.DayOfWeek != DayOfWeek.Sunday) workdays--; });
Console.Out.WriteLine("workdays = {0}", workdays);
}
圣诞节和节礼日作为假期包括在内。