NSDateFormatter意外调整时间问题

时间:2016-06-07 15:19:43

标签: ios objective-c nsdateformatter

在Objective-C中工作,我有一个方法来正确格式化从数据库中获取的日期。 数据库返回没有时区信息的日期和时间。例如'2016-06-07T09:29:50.253'。

问题在于它正确地获取了日期,然后将其恢复了一个小时。对于我09:29的时间,我最终会以08:29结束。

我现在正在与BST合作。

我有以下代码:

    +(NSDate *)getDate:(NSString *)date {

//Gets the date
        date = [date stringByReplacingOccurrencesOfString:@"T" withString:@" "];
        date = [date componentsSeparatedByString: @"."][0];

//Formats the date
        NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
//This line is the one that fixes it.
        [formatter setTimeZone: [NSTimeZone timeZoneWithName:@"UTC"]];
        [formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"];

        NSDate  *returnDate = [formatter dateFromString:date];
        return returnDate;
    }

我做了一些谷歌搜索,发现添加以下行可以解决问题。

[formatter setTimeZone: [NSTimeZone timeZoneWithName:@"UTC"]];

这暂时没问题,但我担心它会在夏令时再次破裂,我不能完全确定为什么要修复它。我也希望能够让它针对不同的时区进行调整,但到目前为止还没有运气。

更多信息:

- 日期来自sql server中的getDate()调用。我对此的理解是,它需要按日期,不了解时区。如果我进行选择呼叫,我会得到结果:'2016-06-07T09:29:50.253'

将问题正式化: 为什么以上代码可以对returnDate进行调整?

2 个答案:

答案 0 :(得分:0)

NSDate对象与使用格式化程序的表示之间存在重要差异:

NSDate对象始终相对于通用时间标准(UTC)。它忽略了夏令时和时区,这是您希望它存储在数据库中的方式(作为UTC时间戳)。

使用格式化程序时,通常用于向用户显示日期。因此,格式化程序将默认使用您当前设备的区域设置来表示日期,因此,如果您的日期是11:00,并且您处于+4时区且没有夏令时,那么您将获得该日期将是15:00。如果有夏令时,时间会略有变化。您想要这种行为,因为这意味着无论您身在何处,用户都会始终获得正确查看日期的相对时间。

除非像你一样,否则你默认格式化程序使用“UTC”语言环境,不应该与“+0”时区混淆。这就是你得到不同日期的原因。

答案 1 :(得分:0)

尝试使用此格式化程序(而不是删除T和。):

let dateLiteral = "2016-06-07T09:29:50.253"

let formatter = NSDateFormatter()
formatter.dateFormat = "yyyy'-'MM'-'dd'T'HH':'mm':'ss.SSS'Z'"
formatter.dateFromString(dateLiteral) // Jun 7, 2016, 9:29 AM