iOS自帶三種日曆,公曆、佛教日曆和日本日曆,要設置日曆能夠進入"設置-通用-語言與地區-日曆"設置,咱們中國使用的iPhone默認設置成公曆。而泰國人使用的iPhone默認設置的日曆是佛教日曆。這樣會致使一樣的代碼在國內顯示正常,去泰國就彷彿穿越了通常。atom
問題:使用NSDate *today = [NSDate date];獲取的當前的時間在國內顯示正常是2017年,而到了泰國卻變成了2056年,這是爲何呢?即便是時區差異,也不能差如此多呀??spa
通過仔細思考,發現語言和地區的設置之中有一個地方能夠設置日曆,進去把公曆改爲佛教日曆,發現原來顯示的2017變成了2056。code
方法一:component
解決辦法:提供一種不受時區、系統日曆、本地化等限制,得到公曆中的正確的年份、月份、時間等的方法。orm
Global.h對象
@property (strong,nonatomic) NSCalendar *calendar; @property (strong,nonatomic) NSDateComponents *components; @property (copy,nonatomic) NSString *year; @property (copy,nonatomic) NSString *month; @property (copy,nonatomic) NSString *day; @property (copy,nonatomic) NSString *hour; @property (copy,nonatomic) NSString *minute; @property (copy,nonatomic) NSString *second;
Global.mblog
- (NSCalendar *)calendar{ if(!_calendar){ #ifdef __IPHONE_8_0 _calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];//根據Identifer獲取公曆 #else _calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];//根據Identifer獲取公曆 #endif _calendar.timeZone = [NSTimeZone localTimeZone];//消除時區差別 _calendar.locale = [NSLocale currentLocale];//消除本地化差別,本地化包括語言、表示的日期格式等 } return _calendar; } - (NSDateComponents *)components{ if (!_components) { NSDate *date = [NSDate date]; _components = [self.calendar components:NSCalendarUnitYear | NSCalendarUnitMonth | NSCalendarUnitDay | NSCalendarUnitHour | NSCalendarUnitMinute | NSCalendarUnitSecond | NSCalendarUnitWeekday fromDate:date]; } return _components; } //返回當前年份 - (NSString *)year{ if (!_year) { _year = [NSString stringWithFormat:@"%04ld",[kGlobal.components year]]; } return _year; } //返回當前月份 -(NSString *)month{ if (!_month) { _month = [NSString stringWithFormat:@"%02ld",[kGlobal.components month]]; } return _month; } //返回當前號數 - (NSString *)day{ if (!_day) { _day = [NSString stringWithFormat:@"%02ld",[kGlobal.components day]]; } return _day; } //返回當前的小時 - (NSString *)hour{ if (!_hour) { _hour = [NSString stringWithFormat:@"%02ld",[kGlobal.components hour]]; } return _hour; } //返回當前的分鐘 - (NSString *)minute{ if (!_minute) { _minute = [NSString stringWithFormat:@"%02ld",[kGlobal.components minute]]; } return _minute; } //返回當前的秒鐘 - (NSString *)second{ if (!_second) { _second = [NSString stringWithFormat:@"%02ld",[kGlobal.components second]]; } return _second; }
2017-02-04更新:string
方法二:正常獲取公曆年月日(系統日曆爲佛教日曆或其餘非公曆日曆)it
1.首先建立一個公曆日曆對象form
- (NSCalendar *)calendar{ if(!_calendar){ #ifdef __IPHONE_8_0 _calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian];//根據Identifer獲取公曆 #else _calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];//根據Identifer獲取公曆 #endif _calendar.timeZone = [NSTimeZone localTimeZone];//消除時區差別 _calendar.locale = [NSLocale currentLocale];//消除本地化差別,本地化包括語言、表示的日期格式等 } return _calendar; }
2.在NSDateFormatter格式化對象的時候加上一條語句就行:[formatter setCalendar:self.calendar];
- (NSDateFormatter *)formatter{ if (!_formatter) { _formatter = [[NSDateFormatter alloc] init]; [_formatter setCalendar:kGlobal.calendar]; [_formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"]; } return _formatter; }
總結:NSDateFormatter若是不設置日曆對象,默認使用的是系統的日曆對象,因此不管你使用什麼方式獲得正確的公曆年月日,若是最後格式化了日期,都會變成系統默認的日曆日期,因此
格式化日期的時候須要設置NSDateFormatter的Calendar對象。同理系統默認的UIDatePicker應該也能夠這麼設置(有待驗證)。