我为我的Android应用程序编写了一些代码,用于检查事件注册是否在下一个小时内。为此,我获得了当前时间,并为此增加了60分钟以获得小时位置的结束时间。这段代码工作正常,但是如果60分钟的时间段进入第二天(如果开始时间是23:11,结束时间是00:11),我认为它不起作用。在检查我的日期对象时,我注意到Android Studio说我的Date对象有一些日期信息(1月1日......)。这很奇怪,因为我指定时间格式只有时间信息。以下是一些代码:
DateFormat timeFormat = new SimpleDateFormat("hh:mm aa", Locale.ENGLISH);
DateFormat dateFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
DateFormat scanDateFormat = new SimpleDateFormat("yyyy/MM/dd");
//Some logic has been cut out
if (currentEventRegistrations.size() > 0) {
//We need to check for the earliest events
Event earliestEvent = null; //Keep a reference to the earlist event
for (int a = 0; a < currentEvents.size(); a++) {
Event thisEvent = currentEvents.get(a);
if (a == 0) {
earliestEvent = thisEvent;
} else {
Date nextEventDate = timeFormat.parse(thisEvent.getTime());
Date currentEventDate = timeFormat.parse(earliestEvent.getTime());
if (nextEventDate.compareTo(currentEventDate) <= 0) {
earliestEvent = thisEvent;
}
}
}
//Now that we have the earliest event happening today, we need to check if it is within 30 minutes
earliestEvent.setTime(earliestEvent.getTime().toUpperCase());
Date earlyEventDate = timeFormat.parse(earliestEvent.getTime());
Calendar now = Calendar.getInstance();
Date later = now.getTime();
String time = timeFormat.format(later);
now.add(Calendar.MINUTE, 60);
String timeEnd = timeFormat.format(now.getTime());
Date laterStart = timeFormat.parse(time);
Date laterEnd = timeFormat.parse(timeEnd);
if (earlyEventDate.compareTo(laterStart) >= 0 && earlyEventDate.compareTo(laterEnd) <= 0)
{ //If the event is in the next 30 minute time frame, save all the event data
finalEvent = earliestEvent;
finalEventRegistration = getEventRegistration(earliestEvent.getEventId());
finalRoute = getRoute(finalEventRegistration.getSelectedRoute());
if (finalEvent!= null && finalEventRegistration != null && finalRoute != null) {
return true;
} else {
return false;
}
}
将时间字符串转换为时间对象的最佳方法是什么?另外,处理可能在第二天重叠的时间框架的最佳方法是什么?
答案 0 :(得分:1)
一种简单的方法是始终以毫秒为单位存储时间。即,使用
获取当前时间long now = System.currentTimeMillis());
对于事件(如果您使用的是日历),请使用
long eventTime = calendar.getTimeInMillis();
然后检查now + 60*60*1000l > eventTime
。
答案 1 :(得分:1)
你似乎工作太辛苦了。你正在使用臭名昭着的旧日期时间类,现在已经遗留下来了,取而代之的是java.time类。
java.time类首先作为Java 8的内置部分到达。大部分java.time功能都被反向移植到Java 6&amp; ThreeTen-Backport中的7,并进一步适应Android中的ThreeTenABP(见How to use…)。
您的代码令人费解。但基本上你似乎想通过文本从用户那里收集一个目标日期时间,看看是否会在下一个小时内到达。
收集数据的最简单方法是要求用户以标准ISO 8601格式输入。
String dateInput = "2016-01-23";
String timeInput = "20:05:00";
在解析/生成表示日期时间值的字符串时,java.time类默认使用标准格式。要使用其他格式,请搜索“{1}}的堆栈溢出。
” Java DateTimeFormatter
类型缺少有关偏离UTC或时区的信息。
Local…
此LocalDate ld = LocalDate.parse( dateInput );
LocalDate lt = LocalTime.parse( timeInput );
LocalDateTime ldt = LocalDateTime.of( ld , lt );
对象不是实际时刻,而不是时间轴上的点。如果没有来自UTC或时区的偏移的上下文,则该值没有实际意义。
您还应该询问用户时区作为该日期时间的参考。或者您可以采用区域,或使用其JVM的当前默认时区。有关详细信息,请搜索LocalDateTime
的堆栈溢出。
Java ZoneId
应用该区域以了解ZoneId z = ZoneId.of( "America/Montreal" );
。应用LocalDateTime
获取ZoneId
,即时间轴上的实际时刻。
ZonedDateTime
将ZonedDateTime zdt = ldt.atZone( z );
对象转换为简单的UTC值。
Instant
类代表UTC中时间轴上的一个时刻,分辨率为nanoseconds(小数部分最多九(9)位)。
ZonedDateTime
获取当前时刻。
Instant instant = zdt.toInstant();
一小时后。
Instant now = Instant.now();
如果您需要在所需/预期时区内向用户显示该时间限制,则可以应用Instant later = now.plus( 1 , ChronoUnit.HOURS );
从Instant
转换为ZonedDateTime
。致电ZoneId
或使用toString
生成字符串进行演示。
DateTimeFormatter
使用半开放式方法,询问您的目标时间(ZonedDateTime zdtNow = now.atZone( z );
ZonedDateTime zdtLater = later.atZone( z );
)是否等于或晚于开头(instant
)且早于结束时间(now
)。说“等于或晚于”的较短方式是“不在之前”。
later
要了解有关半开放式方法逻辑的更多信息,请search Stack Overflow for java time Half-Open
。
更简单的方法是使用Interval
项目提供的ThreeTen-Extra类。
Boolean isTargetWithinTimeFrame =
( ! instant.isBefore( now ) )
&&
instant.isBefore( later )
;
java.time框架内置于Java 8及更高版本中。这些类取代了麻烦的旧日期时间类,例如java.util.Date
,.Calendar
和&amp; java.text.SimpleDateFormat
现在位于Joda-Time的maintenance mode项目建议迁移到java.time。
要了解详情,请参阅Oracle Tutorial。并搜索Stack Overflow以获取许多示例和解释。
从哪里获取java.time类?
ThreeTen-Extra项目使用其他类扩展java.time。该项目是未来可能添加到java.time的试验场。您可以在此处找到一些有用的课程,例如Interval
,YearWeek
,YearQuarter
和more。
答案 2 :(得分:0)
科特琳代码段
#define APPEND_DOT(x) "." STR(x)
#define CONCSTR3(_1, _2, _3) CONCSTR2(_1, _2) APPEND_DOT(_3)
#define CONCSTR2(_1, _2) STR(_1) APPEND_DOT(_2)
#define CONCSTR1(_1) STR(_1)
#define JOIN_STR_DOT(_1, _2, _3) CONCSTR3(_1, _2, _3)
std::string dot_str = JOIN_STR_DOT(one, two, three);
注意: :我忽略了上述函数中的秒,但是您可以添加它并以与分钟类似的方式应用条件。