Ios 防止日期本地化

Ios 防止日期本地化,ios,swift,date,Ios,Swift,Date,我有以下字符串: let dateString = "2018-04-18T04:54:00-04:00" 我通过执行以下操作,通过ISO8601DateForamtter初始化日期: let formatter = ISO8601DateFormatter() let date = formatter.date(from: dateString) Apr 18, 2018 at 1:54am 如果我打印日期,我会得到以下信息: let formatter = ISO8601DateFor

我有以下字符串:

let dateString = "2018-04-18T04:54:00-04:00"
我通过执行以下操作,通过
ISO8601DateForamtter
初始化
日期

let formatter = ISO8601DateFormatter()
let date = formatter.date(from: dateString)
Apr 18, 2018 at 1:54am
如果我打印日期,我会得到以下信息:

let formatter = ISO8601DateFormatter()
let date = formatter.date(from: dateString)
Apr 18, 2018 at 1:54am
格式化程序正在自动将时间转换为我的本地时间。我如何防止我的时区被占用?例如,我希望
Date
对象显示以下内容:

Apr 18, 2018 at 4:54am 

不要直接记录
日期
,而是查看
ISO8601DateFormatter
上的
字符串(from:timeZone:formatOptions:)
方法。这样,您就可以获得所需任何时区的日期字符串。

与其直接记录
日期,不如查看
字符串(from:timeZone:formatOptions:)
方法,该方法位于
ISO8601DateFormatter
。这样,您就可以获得所需任何时区的日期字符串。

您应该将格式化程序设置为适当的时区,例如(下面的UTC示例):

或者根据GMT指定:

formatter.timeZone = TimeZone(secondsFromGMT: 0)

您应该将格式化程序设置为适当的时区,例如(下面的UTC示例):

或者根据GMT指定:

formatter.timeZone = TimeZone(secondsFromGMT: 0)

对于
ISO8601
2018-04-18T04:54:00-04:00
表示
2018-04-18 04:54:00
GMT-4h
中。要以原始字符串的形式打印时间,您需要创建一个带有特定时区的日期格式化程序,该时区为
-4

let dateFormatter = DateFormatter()
dateFormatter.timeZone = TimeZone(secondsFromGMT: -4 * 60 * 60)
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
print(dateFormatter.string(from: date))
你会得到

2018-04-17 04:54:00

仅供参考,我正在为
ISO8601
添加一个链接,
2018-04-18T04:54:00-04:00
表示
2018-04-18 04:54:00
GMT-4h
中。要以原始字符串的形式打印时间,您需要创建一个带有特定时区的日期格式化程序,该时区为
-4

let dateFormatter = DateFormatter()
dateFormatter.timeZone = TimeZone(secondsFromGMT: -4 * 60 * 60)
dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
print(dateFormatter.string(from: date))
你会得到

2018-04-17 04:54:00

仅供参考,我正在为

添加一个链接。您需要从日期字符串解析时区,并使用它从日期格式化程序设置时区:

func secondsFromGMT(from string: String) -> Int {
    guard !string.hasSuffix("Z") else { return 0 }
    let timeZone = string.suffix(6)
    let comps = timeZone.components(separatedBy: ":")
    guard let hours = comps.first,
        let minutes = comps.last,
        let hr = Int(hours),
        let min = Int(minutes) else { return 0 }
    return hr * 3600 + min * 60
}


您需要从日期字符串解析时区,并使用它从日期格式化程序设置时区:

func secondsFromGMT(from string: String) -> Int {
    guard !string.hasSuffix("Z") else { return 0 }
    let timeZone = string.suffix(6)
    let comps = timeZone.components(separatedBy: ":")
    guard let hours = comps.first,
        let minutes = comps.last,
        let hr = Int(hours),
        let min = Int(minutes) else { return 0 }
    return hr * 3600 + min * 60
}


从当前格式化程序接收的日期在技术上是正确的。不建议按照当前接受的答案中所述向后设置日期,因为您实际上是在硬编码预期时区。一旦您的设备进入另一个时区(或者如果用户在当前时区之外下载您的应用程序),您的信息将不正确

如果试图在UTC时区中显示此时间,则需要使用另一个格式化程序在目标时区中正确格式化输出

let utcFormatter = DateFormatter()
utcFormatter.timeZone = TimeZone(secondsFromGMT: 0)
// Perform any other transformations you'd like
let output = utcFormatter.string(from: date)

但是为什么你原来的日期是正确的呢

Date
API非常健壮,可以在幕后做很多事情,但是使用简单的
Double
可以有效地实现。它向您显示的自动时区信息是一种抽象,使其更易于推理。从技术上讲,日期不知道它所在的时区,但将其转换为字符串会隐式地在日期上应用推断的日期格式化程序,并返回它认为对您最有用的信息

如果您正在对某个日期进行操作,则很可能使用
Calendar
API。通常,使用
Calendar.current
会获得一个新实例,该实例将使用当前时区信息创建一个新日历。您可以按如下方式更改日历的时区:

var calendar = Calendar.current
calendar.timeZone = TimeZone(secondsFromGMT: 0)

这将为您提供在任何时区工作的相对日期,而无需修改正在使用的基本
日期
对象。

从当前格式化程序接收的日期在技术上是正确的。不建议按照当前接受的答案中所述向后设置日期,因为您实际上是在硬编码预期时区。一旦您的设备进入另一个时区(或者如果用户在当前时区之外下载您的应用程序),您的信息将不正确

如果试图在UTC时区中显示此时间,则需要使用另一个格式化程序在目标时区中正确格式化输出

let utcFormatter = DateFormatter()
utcFormatter.timeZone = TimeZone(secondsFromGMT: 0)
// Perform any other transformations you'd like
let output = utcFormatter.string(from: date)

但是为什么你原来的日期是正确的呢

Date
API非常健壮,可以在幕后做很多事情,但是使用简单的
Double
可以有效地实现。它向您显示的自动时区信息是一种抽象,使其更易于推理。从技术上讲,日期不知道它所在的时区,但将其转换为字符串会隐式地在日期上应用推断的日期格式化程序,并返回它认为对您最有用的信息

如果您正在对某个日期进行操作,则很可能使用
Calendar
API。通常,使用
Calendar.current
会获得一个新实例,该实例将使用当前时区信息创建一个新日历。您可以按如下方式更改日历的时区:

var calendar = Calendar.current
calendar.timeZone = TimeZone(secondsFromGMT: 0)

这将为您提供在任何时区都可以工作的相对日期,而无需修改您正在使用的基本
日期
对象。

只需使用DateFormatter以所需的日期格式从日期获取本地化字符串。您是如何打印
日期
实例的?date实例基本上是一个没有任何时区信息的时间对象。如果你想指定时区,你需要使用格式化程序。你能解释一下上下文吗?我曾经处理过一个类似的情况,我必须在出发城市的本地时间显示航空公司航班的出发时间,该时间可能与用户所在的时区不同。只需使用DateFormatter在所需的日期格式从您的日期中获取本地化字符串,您是如何打印
日期
实例的?date实例基本上是一个没有任何时区信息的时间对象