NSDate - смещение часового пояса - PullRequest
7 голосов
/ 05 января 2011

Я, должно быть, скучаю по ней, но не могу понять.Пытаюсь создать дату для сравнения, но я не могу сместить currentDate с GMT на EST:

// current date (gmt) //
NSDate *currentDate = [NSDate date];

NSTimeZone *currentDateTimeZone = [NSTimeZone timeZoneWithAbbreviation:@"EST"];

NSDateFormatter *currentDateFormat = [[NSDateFormatter alloc]init];
[currentDateFormat setTimeZone:currentDateTimeZone];
[currentDateFormat setDateFormat:@"yyyy-MM-dd HH:mm:ss zzz"];

NSString *currentDateString = [currentDateFormat stringFromDate:currentDate];
NSLog(@"currentDateString: %@", currentDateString); // returns 2011-01-05 13:30:30 EST

NSDate *currentDateWithOffset = [currentDateFormat dateFromString:currentDateString];

NSLog(@"currentDateWithOffset: %@", currentDateWithOffset); // returns 2011-01-05 18:30:30 +0000

Спасибо!

Редактировать:

Явызывая метод в отдельном классе (пытаясь сделать его переносимым), используя следующую строку:

[Expiration expires:[[NSDate alloc] initWithString:@"2011-01-07 12:00:00 +0000"] within:1.0]

в методе expires у меня есть следующие строки:

NSComparisonResult comparison = [currentDateWithOffset compare:expires]; // check for a fixed date to disable the demo

double withinRange = [installDate timeIntervalSinceDate:currentDateWithOffset]; // check for number of seconds between "within" and the install date

Язатем сравниваем эти два значения следующим образом:

if(withinRange >= within && withinRange > 0.0) {
    // app is expired //
}
else {
    // app is still enabled (so far...) //
    if(comparison == NSOrderedDescending || comparison == NSOrderedSame) {
        // app is expired //
    }
    else {
        // app is still enabled //
    }
}

Помогает ли это?Спасибо за ваше терпение!

Редактировать:

Вот весь срок действия: внутри метода в том виде, в каком он есть в настоящее время ...

+(BOOL)expire:(NSDate*)expires within:(double)within {
   // default expired value //
    BOOL expired = NO;

    // convert within value from days to seconds //
    within *= 24.0 * 60.0 * 60.0;

    // current date (gmt) //
    NSDate *currentDate = [NSDate date];

    // install date //
    NSDate *installDate = [[NSUserDefaults standardUserDefaults]objectForKey:@"installDate"];

    // check for a value in installDate //
    if (nil == installDate) {
        // app is running for the first time //
        [[NSUserDefaults standardUserDefaults]setObject:currentDate forKey:@"installDate"];
        [[NSUserDefaults standardUserDefaults]synchronize];
        installDate = currentDate;
    }

    if([installDate timeIntervalSinceNow] < (-within)) {
        expired = YES;
    }
    else {
        if([expires timeIntervalSinceNow] < 0) {
            expired = YES;
        }
    }

    NSLog(@"installDate:%@", installDate);
    NSLog(@"expires:%@", expires);
    NSLog(@"currentDate:%@", currentDate);

    return expired; 
}

Затем я вызываю его из другогокласс с

message.text = (YES == [Expiration expire:[[NSDate alloc] initWithString:@"2011-01-07 12:00:00 -0500"] within:(0.015625/2)]) ? @"This App is Expired" : @"This App is Active";

При работе в симуляторе (новая установка приложения) NSLog отображал это ...

[Session started at 2011-01-06 10:43:46 -0500.]
2011-01-06 10:43:48.146 TimeBasedDemo[14717:207] installDate:2011-01-06 15:43:48 +0000
2011-01-06 10:43:48.147 TimeBasedDemo[14717:207] expires:2011-01-07 17:00:00 +0000
2011-01-06 10:43:48.147 TimeBasedDemo[14717:207] currentDate:2011-01-06 15:43:48 +0000

Ответы [ 4 ]

17 голосов
/ 28 июня 2011

Ни один из этих ответов не дал мне объект NSDate с текущей локальной датой. Вот как я это сделал:

NSDate *currentDateWithOffset = [NSDate dateWithTimeIntervalSinceNow:[[NSTimeZone localTimeZone] secondsFromGMT]];
5 голосов
/ 05 января 2011

Объект NSDate представляет момент времени независимо от часового пояса и календаря. Информация о часовом поясе важна при печати или разборе даты, но она не сохраняется в NSDate.

Допустим, вы создаете дату истечения срока действия следующим образом:

NSDate *exp=[[NSDate alloc] initWithString:@"2011-01-07 12:00:00 +0000"]

Это говорит о том, что вы хотите, чтобы срок действия истек в полдень по Гринвичу 7 января. Если вы хотите, чтобы срок его действия истекал в полдень EST, создайте его с -0500 вместо этого. , а не , что вам нужно сделать, - это связываться с текущим временем, когда вы проводите сравнение.

Простой способ узнать, прошло ли время, тогда

if ([exp timeIntervalSinceNow]<0) { /* it's expired */ }

и вы можете увидеть, прошло ли within секунд с даты установки, например:

if ([installDate timeIntervalSinceNow]<(-within)]) { /* it's expired */}
0 голосов
/ 05 января 2011

Я немного повозился и нашел способ «обмануть» смещение в соответствии с моими потребностями.Из другого прочтения, я предполагаю, что NSCalendar может быть лучшим долгосрочным решением, но сейчас я закончил тем, что изменил

NSDate *currentDateWithOffset = [currentDateFormat dateFromString:currentDateString];

на

NSDate *currentDateWithOffset = [[NSDate alloc] initWithString:[NSString stringWithFormat:@"%@ +0000", currentDateString]];

Это дало мне результатыМне нужно и работает в последующих сравнениях, которые я использую.Спасибо за справочную информацию всем!

0 голосов
/ 05 января 2011

В Какао NSDate - это абстрактное представление даты без применения информации о часовом поясе.Обратите внимание, что currentDateWithOffset является той же датой, что и строка даты, только в другом часовом поясе (на пять часов вперед).Это ожидаемое поведение, поскольку NSDate не сохраняет часовой пояс, использованный для его создания.

...