Objective-Cでの日付計算

はじめに

こんにちは
ビンゴ中西です。

Objective-Cで日付を扱うのは手順が多くて、覚えるのが大変ですね。
毎回、検索するのもあれなので、ここに書いていきます。

(メモリ管理は適切に補ってください)

追記

このあたりも考慮しないと駄目かも

NSDateFormatterで日付文字列変換する際の注意 - 西海岸より
たいへんですね

現在の時間を取得

NSDate *now = [NSDate date];

まさかの NSDateオブジェクトのdateメソッドを呼ぶだけ。
簡単ですね。

明日の日付

    NSDate *now             = [NSDate date];
    NSCalendar *cal         = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
    NSDateComponents *comps = [[NSDateComponents alloc] init];
    [comps setDay:1];
    NSDate *nextDay         = [cal dateByAddingComponents:comps toDate:now options:0];

NSLogで見てみると.....

NSDate *now             = [NSDate date];
NSLog(@"now : %@", now);

結果:

now : 2012-10-25 07:08:39 +0000

と表示されます。

いやいや僕、日本人ですし おすし

弊社には外国人も多く在籍しておりますが、
ここは日本ですし、僕日本人ですし、イギリスとか行ったことないですし、日本時間で見たいですね。

NSDateFormatterを使うと日本時間(ローカル)の文字列が得れるみたい。

NSDate *now             = [NSDate date];
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
[formatter setDateFormat:@"yyyy-MM-dd HH:mm Z"];
NSString *nowString = [formatter stringFromDate:now];

結果:

now : 2012-10-25 16:17 +0900

んー カレンダークラス使うのめんどくさい.....

カレンダークラス使うのめんだくさいですね。
今何の処理書いてたのか、なんのクラス操作してるのか、短い行数なのに頭がパニックになります。
NSDateからいきなり明日を取得しましょう。

NSDate *nextDay = [NSDate dateWithTimeIntervalSinceNow:1*24*60*60];

でもこれ、うるう秒のとき駄目感ありですね。明日は24時間と1秒後かもしれませんしね。こわいよお><
そこまで厳密にするシステムもめずらしいですが。

明日になった瞬間!つまり0時を取得したい!

    NSDate *nextDay = [NSDate dateWithTimeIntervalSinceNow:1*24*60*60];

    NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
    [formatter setDateFormat:@"yyyy-MM-dd"];
    NSDate *nextDayZero = [formatter dateFromString:[formatter stringFromDate:nextDay]];

    NSLog(@"nextDayの0時:%@", nextDayZero);

今から24時間後を取得して、
一度NSStringにしてNSDateにもどすことで、00:00:00を補ってもらう手法です。
うるう秒のときが心配ですね。。。。 うるう秒め!!!!

setDayとの合わせ技で明日の0時を取得してみよう

    NSDate *now             = [NSDate date];
    NSCalendar *cal         = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
    NSDateComponents *comps = [[NSDateComponents alloc] init];
    [comps setDay:1];
    NSDate *nextDay         = [cal dateByAddingComponents:comps toDate:now options:0];
    
    NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
    [formatter setDateFormat:@"yyyy-MM-dd"];
    NSDate *nextDayZero = [formatter dateFromString:[formatter stringFromDate:nextDay]];
    
   NSLog(@"明日の0時 : %@", nextDayZero);

まとめ

  • NSDateはデフォルトで今の時刻を知っている
  • NSDateはユニックスタイムみたいにある時刻からの経過時間を持ってるだけなので、秒数で足し算引き算は得意だけど、明日とかの計算はNSCalendar使わないといけない
  • NSDateFormatterはデフォルトでローカルを知っている