LoginSignup
8
7

More than 5 years have passed since last update.

iOSでDateをyyyy-MM-ddにフォーマットするベンチマーク

Posted at

NSDateFormatterが遅いらしいというのは聞くので、
2017-05-10 形式にフォーマットする速度を、実際に計測してみました。

  • NSDateFormatter (インスタンスをキャッシュしない/する)
  • time_t + String(format:)
  • time_t + strftime

結果

iPhone6 plus にて。

実機 Simulator
DateFormatter 18.274 9.317
DateFormatter shared instance 1.455 0.592
localtime + String(format:) 1.347 4.036
localtime + strftime 0.612 6.411

Listなど、同じフォーマットをたくさん処理するなら、
とりあえずDateFormatterのインスタンスを共有するようにしとけば良さそう。
iOS7未満もサポートするなら、strftimeを使えばいいんじゃないか。

Simulatorでlocaltime使うと妙に遅い理由は何なんだろう。

コード

swift2.3です
func benchmark(@noescape closure: (NSDate) -> Void) -> NSTimeInterval{
    let count = 100_000
    let date = NSDate()
    let start = date
    (0..<count).forEach { _ in
        closure(date)
    }
    return NSDate().timeIntervalSinceDate(start)
}

// DateFormatter
let t1 = benchmark() { (date) in
    let formatter = NSDateFormatter()
    formatter.dateFormat = "yyyy-MM-dd"
    formatter.locale = NSLocale(localeIdentifier: "en_US_POSIX")
    let str = formatter.stringFromDate(date)
}

// DateFormatter shared instance
let formatter = NSDateFormatter()
formatter.dateFormat = "yyyy-MM-dd"
formatter.locale = NSLocale(localeIdentifier: "en_US_POSIX")
let t2 = benchmark { (date) in
    let str = formatter.stringFromDate(date)
}

// localtime + String(format:)
let t3 = benchmark { (date) in
    var timeValue = Int(date.timeIntervalSince1970) as time_t
    let tmValue = localtime(&timeValue)
    let str = String(format: "%04d-%02d-%02d", tmValue.memory.tm_year + 1900, tmValue.memory.tm_mon + 1, tmValue.memory.tm_mday)
}

// localtime + strftime
let t4 = benchmark { (date) in
    let bufferSize = 11
    let buffer = UnsafeMutablePointer<Int8>.alloc(bufferSize)
    var timeValue = Int(date.timeIntervalSince1970) as time_t
    let tmValue = localtime(&timeValue)
    let len = strftime(buffer, bufferSize, "%Y-%m-%d", tmValue);
    let str = NSString(bytes: buffer, length: len, encoding: NSASCIIStringEncoding)
    buffer.destroy()
}

print(String(format:"DateFormatter %4.3f seconds", t1))
print(String(format:"DateFormatter shared instance %4.3f seconds", t2))
print(String(format:"localtime + String(format:) %4.3f seconds", t3))
print(String(format:"localtime + strftime %4.3f seconds", t4))

補足

8
7
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
8
7