C# 从有效日期开始计算小时数
我有一个小问题,因为我并不总是了解如何使用当天的课程,例如,我希望列表中的时间从该日期重新计算当天的时间,但如果我有一个新时间,则转换从新时间开始计算。如果我只有一次,它对我来说很好,但是如果我有两次,C# 从有效日期开始计算小时数,c#,C#,我有一个小问题,因为我并不总是了解如何使用当天的课程,例如,我希望列表中的时间从该日期重新计算当天的时间,但如果我有一个新时间,则转换从新时间开始计算。如果我只有一次,它对我来说很好,但是如果我有两次,foreach循环计算我一天中的两次 这是我的代码: public TimeSpan GetHoursForDay(DateTime day) { TimeSpan time = TimeSpan.Zero; foreach (var times in s
foreach
循环计算我一天中的两次
这是我的代码:
public TimeSpan GetHoursForDay(DateTime day) {
TimeSpan time = TimeSpan.Zero;
foreach (var times in shouldWorkTime)
{
if (times.Valid_from > day) //here's the real problem for me, do i want the hours to count from that date, for example: for 1.1.2020 it doesn't need to take hours from 1.12.2019
continue;
if (day.DayOfWeek == DayOfWeek.Monday)
{
time += times.ShouldWorkMonday;
}
if (day.DayOfWeek == DayOfWeek.Tuesday)
{
time += times.ShouldWorkTuesday;
}
if (day.DayOfWeek == DayOfWeek.Wednesday)
{
time += times.ShouldWorkWednesday;
}
if (day.DayOfWeek == DayOfWeek.Thursday)
{
time += times.ShouldWorkThursday;
}
if (day.DayOfWeek == DayOfWeek.Friday)
{
time += times.ShouldWorkFriday;
}
if (day.DayOfWeek == DayOfWeek.Saturday)
{
time += times.ShouldWorkSaturday;
}
if (day.DayOfWeek == DayOfWeek.Sunday)
{
time += times.ShouldWorkSunday;
}
}
return time;
}
}
以下是我在列表中得到的值:
var shouldWorkTime = new List<ShouldWorkTime>
{
new ShouldWorkTime
{
Valid_from = new DateTime(2019, 12, 01, 0, 0, 0),
ShouldWorkMonday = new TimeSpan(8,0,0),
ShouldWorkTuesday= new TimeSpan(7,0,0),
ShouldWorkWednesday= new TimeSpan(6,0,0),
ShouldWorkThursday= new TimeSpan(5,0,0),
ShouldWorkFriday= new TimeSpan(8,0,0),
ShouldWorkSaturday = new TimeSpan(0,0,0),
ShouldWorkSunday = new TimeSpan(0,0,0)
},
new ShouldWorkTime
{
Valid_from = new DateTime(2020, 01, 01, 0, 0, 0),
ShouldWorkMonday = new TimeSpan(4,0,0),
ShouldWorkTuesday= new TimeSpan(3,0,0),
ShouldWorkWednesday= new TimeSpan(6,0,0),
ShouldWorkThursday= new TimeSpan(5,0,0),
ShouldWorkFriday= new TimeSpan(9,0,0),
ShouldWorkSaturday = new TimeSpan(0,0,0),
ShouldWorkSunday = new TimeSpan(0,0,0)
}
};
var shouldWorkTime=新列表
{
新工作时间
{
有效期从=新日期时间(2019、12、01、0、0、0),
ShouldWorkMonday=新的时间跨度(8,0,0),
shouldWork星期二=新的时间跨度(7,0,0),
shouldWork星期三=新的时间跨度(6,0,0),
shouldWork周四=新的时间跨度(5,0,0),
ShouldWorkFriday=新的时间跨度(8,0,0),
shouldWorkstatudy=新的时间跨度(0,0,0),
shouldWorkshanday=新的时间跨度(0,0,0)
},
新工作时间
{
有效期从=新日期时间(2020,01,01,0,0),
ShouldWorkMonday=新的时间跨度(4,0,0),
shouldWork星期二=新的时间跨度(3,0,0),
shouldWork星期三=新的时间跨度(6,0,0),
shouldWork周四=新的时间跨度(5,0,0),
ShouldWorkFriday=新的时间跨度(9,0,0),
shouldWorkstatudy=新的时间跨度(0,0,0),
shouldWorkshanday=新的时间跨度(0,0,0)
}
};
对于day值,我总是从日历中获取当前日期的值,因此在本例中,我希望计算1.1.2020的天数,即第二次计算的天数,以及在此之前第一次计算的天数
因此,我需要返回一个工人在某一天需要工作多少小时,但从最后一个日期开始生效(valid_from)
我怎样才能纠正这个问题?非常感谢你们的帮助
例如:
输入1.1.2020输出=6,0,0
输入1.12.2019输出=0,0,0
如果
day
的值足够大,则对于shouldWorkTime
中的所有元素,测试times.Valid\u from>day
为false
。这就是为什么time
可以多次递增的原因
如果您只想在中第一个/最后一个可接受的Valid\u值上增加一次,则应确保应工作时间
按递增/递减顺序排序,并确保仅增加一次
实际上,您不需要增量,只需返回相应的TimeSpan
:
public TimeSpan GetHoursForDay(DateTime day) {
// shouldWorkTime should have been sorted once for all at creation.
// This code use the first acceptable Valid_from
// By using OrderByDescending we take the last (in date) entry
var math = shouldWorkTime
.Where(v => day >= v.Valid_from) // We take only valid entry
.OrderByDescending(v => v.Valid_from) // We sort only on valid entry
.FirstOrDefault(); // we take the last (in date) valid entry
if (match == null)
return TimeSpan.Zero;
switch (day.DayOfWeek)
{
case DayOfWeek.Monday:
return match.ShouldWorkMonday;
case DayOfWeek.Tuesday:
return match.ShouldWorkTuesday;
case DayOfWeek.Wednesday:
return match.ShouldWorkWednesday;
case DayOfWeek.Thursday:
return match.ShouldWorkThursday;
case DayOfWeek.Friday:
return match.ShouldWorkFriday;
case DayOfWeek.Saturday:
return match.ShouldWorkSaturday;
case DayOfWeek.Sunday:
return match.ShouldWorkSunday;
}
}
编辑:
为了避免代码重复,ShouldWorkTime
类可以提供一个GetWorkTimeOrDayOfWeek
:
public TimeSpan GetWorkTimeForDayOfWeek(DayOfWeek dayOfWeek) {
...
}
您可以查看集合,而不是在七个字段中存储七个值。我将选择一个。这里是对数据结构的一点修改。
TimeSpan将使用字典映射到DayOfWeek,而不是属性的早午餐。这将消除对开关箱或大量If的需要。
使用DayOfWeek作为字典键可确保一天只定义一个TimeSpan
public class WorkingTimeScheldure
{
public DateTime Start { get; set; }
public DateTime End { get; set; }
public Dictionary<DayOfWeek, TimeSpan> Scheldure { get; set; }
}
结果:
12/01/2019 , it's a Sunday I have to work 0 Hour!
12/02/2019 , it's a Monday I have to work 8 Hours!
12/03/2019 , it's a Tuesday I have to work 7 Hours!
12/04/2019 , it's a Wednesday I have to work 6 Hours!
12/05/2019 , it's a Thursday I have to work 5 Hours!
12/06/2019 , it's a Friday I have to work 8 Hours!
12/07/2019 , it's a Saturday I have to work 0 Hour!
12/08/2019 , it's a Sunday I have to work 0 Hour!
01/01/2020 , it's a Wednesday I have to work 6 Hours!
01/02/2020 , it's a Thursday I have to work 5 Hours!
01/03/2020 , it's a Friday I have to work 9 Hours!
01/04/2020 , it's a Saturday I have to work 0 Hour!
01/05/2020 , it's a Sunday I have to work 0 Hour!
01/06/2020 , it's a Monday I have to work 4 Hours!
01/07/2020 , it's a Tuesday I have to work 3 Hours!
01/08/2020 , it's a Wednesday I have to work 6 Hours!
对不起,这个问题我读了很多遍。现在还不清楚,也很难理解。你可以简化一下吗?也许你只是错过了if..@xdtTransform之间的else,所以我需要返回一个工人在某一天需要工作多少小时,但从最后一个日期算起有效,从(valid_from)@xdtTransform我不知道你不清楚的是什么,我尽可能简单,我应该最终返回一周中某一天的时间,但从某个日期开始总是有效的。@Mara试着给我们举一个没有代码的例子,我也不明白你的问题。@Mara,当你复制粘贴一些代码,使其具有7倍于(相当)相同代码时,是时候考虑因式分解了。也许你应该告诉你订购的部分(如果我需要从你的有效日期开始),不一定是最后日期,但如果是2019年12月5日(有效期为2019年12月1日),但如果是2020年1月1日,那么他从2020年1月1日开始。通过这段代码,我得到了一个类似的结果。我没有真正理解你的观点,但从我得到的结果来看,也许可以尝试.OrderByDescending(v=>v.Valid\u from).FirstOrDefault(v=>v.Valid\u from>=day)
使用>=
而不是原始问题中的
@Mara,您没有提供规则来申请选择列表中的ShouldWorkTime
项。比如“我想使用最后一个项目(由<代码>有效\u从<代码>订购)作为<代码>有效\u从<代码>+1。Imo,完美的解决方案。选择正确的“匹配”,我选择了<代码>。最后一个(x=>x。开始您的代码很好,但我不能使用Dictionary属性,我是否每天从数据库中获取适当的小时数。您是否可以关闭Dictionary属性并获取此结果。在原始方法中添加var workingTime=shouldWorkTime.Last(x=>x.Start如何恢复timespan.Zero以避免在这一部分上打扰我?var workingTime=WorkingTimeScheldure.Last(x=>x.Start@Mara,把这一部分放在horace的答案中,在他使用firstordefault的地方。我们的答案中没有mutch。它们非常匹配一对一。你应该花点时间用谷歌搜索“linq”“+以下{”OrderBy“,”FirstOrDefault“,”LastOrDefault“,”Last“,”First“}中的一个,以便更好地了解它的工作方式和您正在做的事情。
12/01/2019 , it's a Sunday I have to work 0 Hour!
12/02/2019 , it's a Monday I have to work 8 Hours!
12/03/2019 , it's a Tuesday I have to work 7 Hours!
12/04/2019 , it's a Wednesday I have to work 6 Hours!
12/05/2019 , it's a Thursday I have to work 5 Hours!
12/06/2019 , it's a Friday I have to work 8 Hours!
12/07/2019 , it's a Saturday I have to work 0 Hour!
12/08/2019 , it's a Sunday I have to work 0 Hour!
01/01/2020 , it's a Wednesday I have to work 6 Hours!
01/02/2020 , it's a Thursday I have to work 5 Hours!
01/03/2020 , it's a Friday I have to work 9 Hours!
01/04/2020 , it's a Saturday I have to work 0 Hour!
01/05/2020 , it's a Sunday I have to work 0 Hour!
01/06/2020 , it's a Monday I have to work 4 Hours!
01/07/2020 , it's a Tuesday I have to work 3 Hours!
01/08/2020 , it's a Wednesday I have to work 6 Hours!