NSCalendar的components:fromDate:方法未填充NSCalendarUnitHour的原因排查求助
嘿,这个问题我之前帮不少开发者排查过类似的,结合你的代码和给出的日期信息,大概率是这几个原因导致的,咱们一个个捋:
时区转换的边界情况
你的result是UTC时间2018-03-18 05:48:36 +0000,但你把日历的时区设成了本地时区。举个例子,如果你的本地时区是西五区(UTC-5),转换后本地时间是前一天的22:48,小时是存在的;但如果是某些有夏令时切换的时区,刚好在转换时遇到时间调整的边界,可能会出现组件提取异常?你可以先打印下本地时区的详细信息看看:NSLog(@"Local Time Zone: %@", [NSTimeZone localTimeZone]);同时计算下UTC时间转本地时间后的具体值,确认小时部分到底是什么。
别误读了组件属性
你是不是在获取小时的时候用错了属性?比如把resultComponents.hour写成了resultComponents.hourOfDay?不对,NSCalendarUnitHour对应的就是hour属性。保险起见,直接打印所有提取的组件看看实际值:NSLog(@"Day: %ld, Month: %ld, Hour: %ld, Minute: %ld", (long)resultComponents.day, (long)resultComponents.month, (long)resultComponents.hour, (long)resultComponents.minute);如果hour是0,那可能是时区转换后的结果;如果是nil,那才是真的没被填充。
先排除时区干扰
你可以先创建一个不设置时区的日历实例,直接提取UTC时间的小时组件,看看是否正常:NSCalendar* testCal = [NSCalendar calendarWithIdentifier:NSCalendarIdentifierGregorian]; NSDateComponents* testComponents = [testCal components:NSCalendarUnitHour fromDate:result]; NSLog(@"UTC Hour: %ld", (long)testComponents.hour); // 正常应该输出5如果这个输出正常,那问题肯定出在本地时区的转换上,再针对性排查时区的问题就行。
位运算有没有写错?
你用NSCalendarUnitDay | NSCalendarUnitHour | NSCalendarUnitMinute | NSCalendarUnitMonth组合组件的写法是对的,但有没有可能手滑拼错了NSCalendarUnitHour?比如写成了NSCalendarUnitMinute两次?不过看你给出的代码是对的,这条可以先排除。
总结下来,最快速的排查路径就是先验证无时区的组件提取是否正常,再看本地时区转换后的实际时间,就能定位到问题啦。
内容的提问来源于stack exchange,提问作者Sashah

