2015-10-16 11 views
2

所以在我的應用程序中,我需要處理日期,如\/Date(1440156888750-0700)\/,我認爲第一部分代表從1970年1月1日開始的秒數,第二部分代表時區。 我不知道如何處理這樣的數據,並使用Swift 2在Xcode 7中以大家都瞭解的方式顯示它?如何將日期轉換爲/Date(1440156888750-0700) /爲Swift可以處理的內容?

+0

您從哪裏得到這個日期/字符串?此外,閱讀[NSDate類參考](https://developer.apple.com/library/ios/documentation/Cocoa/Reference/Foundation/Classes/NSDate_Class/index.html)可能會幫助你。 – Arc676

+1

小修正,第一部分是從1970年開始* milli *秒。 – luk2302

回答

2

有點實驗後圍繞我想出了以下解決方案:

let dx = "/Date(1440156888750-0700)/" 
let timestamp = (dx as NSString).substringWithRange(NSRange(location: 6,length: 13)) 
let timezone = (dx as NSString).substringWithRange(NSRange(location: 19,length: 5)) 
let dateIntermediate = NSDate(timeIntervalSince1970: Double(timestamp)!/1000) 

let outp = NSDateFormatter() 
outp.dateFormat = "dd.MM.yyyy hh:mm::ssSSS" 
outp.timeZone = NSTimeZone(forSecondsFromGMT: 0) 

let input = outp.stringFromDate(dateIntermediate) + " " + timezone 
let inp = NSDateFormatter() 
inp.dateFormat = "dd.MM.yyyy hh:mm::ssSSS Z" 

let finalDate = inp.dateFromString(input) 
print(finalDate) 

讓我解釋一下:

  • 我們提取原始字符串毫秒時間戳和時區
  • 我們從時間戳創建一個日期,以便能夠將其分成不同的組件
  • 我們以更標準的方式輸出該日期(而不是時間戳)與先前提取的時區追加到該字符串
  • 我們再讀取該字符串並從中重新分析日期


正如@ Phoen1xUK提到的時間戳可能有不同的長度超過13位數字。您可以通過刪除/Date()/,然後在-(或+)之前拆分字符串來處理該情況。

+0

繼續@ WhiteRice的問題,這是一個很好的答案,但是您對1970年以來的毫秒數(unix/posix/epoch時間),所以你不需要將時間戳除以1000. –

+0

@ Phoen1xUK我必須劃分,因爲時間間隔是秒,小數部分表示毫秒 – luk2302

+0

'NSTimeInterval總是在秒;它在10,000年的範圍內產生亞毫秒的精度。' – luk2302

5

(這個答案的前一個版本實際上是錯誤的,它沒有正確處理的時區。)

根據Stand-Alone JSON Serialization

DateTime值出現在表單JSON字符串「/ Date(700000 + 0500)/」,其中第一個數字(提供示例中爲700000)是GMT時區中的毫秒數,即自1970年1月1日午夜以來的正常(非夏令時)時間。這個數字可能是負數,代表早些時候。示例中由「+0500」組成的部分是可選的,並指示時間爲本地類型,即在反序列化時應轉換爲本地時區。如果它不存在,則將時間反序列化爲Utc。實際數字(本例中爲「0500」)及其符號(+或 - )被忽略。

Use JSON.NET to parse json date of format Date(epochTime-offset)

...在此[扭曲格式] [1]中,時間戳部分仍然只基於UTC。偏移量是額外信息。它不會更改時間戳。您可以給出不同的偏移量,或者完全忽略它,它仍然是相同的時間。

\/Date(1440156888750-0700)\/的第一個數字是 毫秒因爲「時代」 1970年1月1日GMT時間 區部分-0700必須僅僅是忽略的數量,和。

這裏是Date一個夫特3擴展方法,其檢查 是字符串的有效性與正則表達式 (可接受\/Date(...)\//Date(...)/,有或沒有 一個時區規範)並轉換給定的數的 毫秒到Date

extension Date { 
    init?(jsonDate: String) { 

     let pattern = "\\\\?/Date\\((\\d+)(([+-]\\d{2})(\\d{2}))?\\)\\\\?/" 
     let regex = try! NSRegularExpression(pattern: pattern) 
     guard let match = regex.firstMatch(in: jsonDate, range: NSRange(location: 0, length: jsonDate.utf16.count)) else { 
      return nil 
     } 

     // Extract milliseconds: 
     let dateString = (jsonDate as NSString).substring(with: match.rangeAt(1)) 
     // Convert to UNIX timestamp in seconds: 
     let timeStamp = Double(dateString)!/1000.0 
     // Create Date from timestamp: 
     self.init(timeIntervalSince1970: timeStamp) 
    } 
} 

實施例:

let jsonDate = "\\/Date(1440156888750-0700)\\/" 
print("JSON Date:", jsonDate) 

if let theDate = Date(jsonDate: jsonDate) { 
    print("Date:", theDate) 
} else { 
    print("wrong format") 
} 

輸出:

 
JSON Date: \/Date(1440156888750-0700)\/ 
Date: 2015-08-21 11:34:48 +0000

更新斯威夫特4:

extension Date { 
    init?(jsonDate: String) { 

     let pattern = "\\\\?/Date\\((\\d+)(([+-]\\d{2})(\\d{2}))?\\)\\\\?/" 
     let regex = try! NSRegularExpression(pattern: pattern) 
     guard let match = regex.firstMatch(in: jsonDate, range: NSRange(jsonDate.startIndex..., in: jsonDate)) else { 
      return nil 
     } 

     // Extract milliseconds: 
     let dateString = jsonDate.substring(with: Range(match.range(at: 1), in: jsonDate)!) 
     // Convert to UNIX timestamp in seconds: 
     let timeStamp = Double(dateString)!/1000.0 
     // Create Date from timestamp: 
     self.init(timeIntervalSince1970: timeStamp) 
    } 
} 
+0

我想過這樣的解決方案 - 只是從時間戳日期基於時區添加或刪除TimeInterval,但我不喜歡這樣的事實完全丟失原始字符串中存在的任何時區信息。 – luk2302

+0

@ luk2302:我不明白你的意思。 「+ -HHMM」轉換爲以秒爲單位的時區偏移量以調整時間值。沒有信息丟失。 –

+0

我的意思是返回格林威治標準時間的正確日期 - 是。但是你放棄了原始日期在不同時區給出的信息。最終輸出中+0000表示的數值恰好 - 您在時區信息中丟失了-0700。 – luk2302

相關問題