[英]Determine if time falls in designated hour range
I am new at C#. 我是C#的新手。 I'd like to check whether a time is between 2 given hours, and if so then do something.
我想检查时间是否在2个给定小时之间,如果是,那么就做点什么。 Can anyone give me an example?
谁能举个例子?
pseudocode example: 伪代码示例:
int starthour = 17;
int endhour = 2;
if ( hour between starthour and endhour){
dosomething();
}
How do I write a check on whether hour
is between starthour
and endhour
? 如何检查
hour
是否在starthour
和endhour
hour
之间? In C#, the time is returned in AM/PM format so I don't know if it will understand the 17
number as "5 PM". 在C#中,时间以AM / PM格式返回,因此我不知道它是否会将
17
号码理解为“5 PM”。
Assuming you're talking about the current time, I'd do something like this: 假设你在谈论当前时间,我会做这样的事情:
// Only take the current time once; otherwise you could get into a mess if it
// changes day between samples.
DateTime now = DateTime.Now;
DateTime today = now.Date;
DateTime start = today.AddHours(startHour);
DateTime end = today.AddHours(endHour);
// Cope with a start hour later than an end hour - we just
// want to invert the normal result.
bool invertResult = end < start;
// Now check for the current time within the time period
bool inRange = (start <= now && now <= end) ^ invertResult;
if (inRange)
{
DoSomething();
}
Adjust the <=
in the final condition to suit whether you want the boundaries to be inclusive/exclusive. 在最终条件下调整
<=
以适合您是否希望边界包含/排除。
If you're talking about whether a time specified from elsewhere is within a certain boundary, just change "now" for the other time. 如果您在谈论从其他地方指定的时间是否在某个边界内,则只需在另一时间更改“现在”。
Actually, if we're dealing with pure hours here like a Abelian Ring from 0 to 23 and 0 again, I believe the following is actually a working solution: 实际上,如果我们在这里处理纯粹的时间,比如0到23和0的阿贝尔环,我相信以下实际上是一个有效的解决方案:
(start <= end && start <= t && t <= end) or (start > end && (start <= t || t <= end))
Complex though this is, it is essentially an if-else where you have a different algorithm depending on whether start <= end or not, where t
is the time you wish to test. 虽然复杂,但它本质上是一个if-else,你有一个不同的算法,取决于start <=是否,其中
t
是你想要测试的时间。 In the first case, start and end are normal order, so t must be both greater than start and less than end. 在第一种情况下,start和end是正常顺序,因此t必须大于start且小于end。 In the case where start is greater than end, the times outside the opposite range are what we want:
在start大于end的情况下,相反范围之外的时间是我们想要的:
Using DeMorgan's theorem: 使用德摩根定理:
This should solve your and my problems. 这应该解决你和我的问题。
@JonSkeet @JonSkeet
The thing is, looking at your algorithm, let's assume for a moment the time is 1am, day 1. 问题是,看看你的算法,让我们暂时假设时间是凌晨1点,第1天。
Now, unless I'm mistaken, start ≰ now since start is 5pm Day 1 and now is 1am Day 1 which is before now, therefore the test fails but the original question wanted 1am included in the range since 1am is between 5pm and 2am. 现在,除非我弄错了,现在开始≰现在从第1天开始是下午5点,现在是第1天,也就是现在之前的第1天,因此测试失败,但原始问题需要凌晨1点,因为凌晨1点是凌晨5点到凌晨2点。 Did I miss something?
我错过了什么?
@Brian @布赖恩
Also, looking at your code, I think you can detect 1am but now you would have a problem with 10pm (22:00) since your times become: 此外,看看你的代码,我认为你可以检测到凌晨1点,但现在你会遇到问题,因为你的时间变成了下午10点(22:00):
Clearly, the general case is very tricky! 显然,一般情况非常棘手! More so when you're restricted to Google Spreadsheets as I am.
当你像我一样被限制在Google Spreadsheets时更是如此。
When subtracting DateTime
s, you get a TimeSpan
struct that you can query for things like the total number of hours (the TotalHours
property): 当减去
DateTime
,你会得到一个TimeSpan
结构,你可以查询总小时数( TotalHours
属性):
TimeSpan ts = starttime - endtime;
if(ts.TotalHours > 2)
{
dosomething();
}
If you want to see if the times are identical , then you can use TotalMilliseconds
- for identical DateTime
s, this will be equal to 0. 如果要查看时间是否相同 ,则可以使用
TotalMilliseconds
- 对于相同的DateTime
,它将等于0。
If you want to compare minutes also like I do you can use this snippet of code in java. 如果你想像我一样比较分钟,你可以在java中使用这段代码。
//Initialize now, sleepStart, and sleepEnd Calendars
Calendar now = Calendar.getInstance();
Calendar sleepStart = Calendar.getInstance();
Calendar sleepEnd = Calendar.getInstance();
//Assign start and end calendars to user specified star and end times
long startSleep = settings.getLong("startTime", 0);
long endSleep = settings.getLong("endTime", 0);
sleepStart.setTimeInMillis(startSleep);
sleepEnd.setTimeInMillis(endSleep);
//Extract hours and minutes from times
int endHour = sleepEnd.get(Calendar.HOUR_OF_DAY);
int startHour = sleepStart.get(Calendar.HOUR_OF_DAY);
int nowHour = now.get(Calendar.HOUR_OF_DAY);
int endMinute = sleepEnd.get(Calendar.MINUTE);
int startMinute = sleepStart.get(Calendar.MINUTE);
int nowMinute = now.get(Calendar.MINUTE);
//get our times in all minutes
int endTime = (endHour * 60) + endMinute;
int startTime = (startHour * 60) + startMinute;
int nowTime = (nowHour * 60) + nowMinute;
/*****************What makes this 100% effective***************************/
//Test if end endtime is the next day
if(endTime < startTime){
if(nowTime > 0 && nowTime < endTime)
nowTime += 1440;
endTime += 1440;
}
/**************************************************************************/
//nowTime in range?
boolean inRange = (startTime <= nowTime && nowTime <= endTime);
//in range so calculate time from now until end
if(inRange){
int timeDifference = (endTime - nowTime);
now.setTimeInMillis(0);
now.add(Calendar.MINUTE, timeDifference);
sleepInterval = now.getTimeInMillis() / 1000;
editor.putBoolean("isSleeping", true);
editor.commit();
Log.i(TAG, "Sleep Mode Detected");
returned = true;
}
Using Jon Skeet's solution above I added a fix where if start time is after beginning time eg You start the job after 6pm at night and end it the next morning at 5am. 使用Jon Skeet上面的解决方案,我添加了一个修复,如果开始时间是在开始时间之后,例如,您在晚上6点之后开始工作,并在第二天早上5点结束。 then you need to check this and apply another day to the end time.
然后你需要检查这个并在结束时间再应用一天。 Hope it helps, I personally have spent too much time on this piece of work.
希望它有所帮助,我个人花了太多时间在这项工作上。 have a great day :)
祝你有美好的一天 :)
if (stopHour < startHour)
{
end = today.AddHours(stopHour+24);
}
Full Code is below. 完整代码如下。
private static bool IsInRunHours()
{
try
{
ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None).Save(ConfigurationSaveMode.Modified);
ConfigurationManager.RefreshSection("appSettings");
// after = 18 before = 5
// Only take the current time once; otherwise you could get into a mess if it
// changes day between samples.
DateTime now = DateTime.Now;
DateTime today = now.Date;
Int32 startHour = ConfigurationManager.AppSettings["UpdateRunAfter"].ToInt();
Int32 stopHour = ConfigurationManager.AppSettings["UpdateRunBefore"].ToInt();
DateTime start = today.AddHours(startHour);
DateTime end = today.AddHours(stopHour);
if (stopHour < startHour)
{
end = today.AddHours(stopHour+24);
}
//ConfigurationManager.AppSettings["UpdateRunBefore"].ToInt()
//ConfigurationManager.AppSettings["UpdateRunAfter"].ToInt()
// Cope with a start hour later than an end hour - we just
// want to invert the normal result.
bool invertResult = end < start;
// Now check for the current time within the time period
bool inRange = (start <= now && now <= end) ^ invertResult;
if (inRange)
{
return true;
}
else
{
return false;
}
}
catch
{
return false;
}
}
bool CheckHour(DateTime check, DateTime start, DateTime end)
{
if (check.TimeOfDay < start.TimeOfDay)
return false;
else if (check.TimeOfDay > end.TimeOfDay)
return false;
else
return true;
}
int starthour = 17;
int endhour = 2;
int nowhour = DateTime.Now.Hour;
if (endhour < starthour)
{
endhour+=24;
nowhour+=24;
}
if (starthour <= nowhour && nowhour <= endhour)
{
dosomething();
}
I'm not sure which I prefer between this code and Jon Skeet's code . 我不确定这个代码和Jon Skeet的代码之间我更喜欢哪个。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.