NSDate、NSCalendar和timezone的關係

NSDate是ios中的一個保存時間的對象,其中包含了時區。通過NSLog輸出的[NSDate date]是GTM時區的時間,是0時區。而中國大陸採用的是正8區。

NSLog(@"GTM 時間:%@",[NSDate date]);

2013-07-09 15:16:38.007 demo[14267:13d03] GTM 時間:2013-07-09 07:16:38 +0000

通過NSDateFormatter將NSDate類的對象輸出設置好的格式。NSDateFormatter採用ios操作系統的時區作爲默認值。操作系統的時區通過[[NSTimeZone localTimeZone] name]獲取到。

    NSLog(@"[[NSTimeZone localTimeZone] name] is %@",[[NSTimeZone localTimeZone] name]);
    
    
    NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init];
    
    
    [dateFormatter setDateFormat:@"YYYY-MM-d HH:mm:ss"];

將NSDateFormatter對象的時區設置"Asia/Shanghai" ,爲正8區,輸出結果就是我們現在看到的時間
    
    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"Asia/Shanghai"]];
    
    NSString *dStr = [dateFormatter stringFromDate:[NSDate date]];
    
    NSLog(@"時區:%@ 當地時間:%@",[[dateFormatter timeZone] name], dStr);

    將NSDateFormatter對象的時區設置"GMT" ,爲0區,輸出結果就是看到[NSDate date]的值。
    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"GMT"]];
    dStr = [dateFormatter stringFromDate:[NSDate date]];
    
    NSLog(@"時區:%@ 當地時間:%@",[[dateFormatter timeZone] name], dStr);
 

將NSDateFormatter對象的時區設置"Asia/Tokyo" ,爲正9區,輸出結果就是日本用戶看到的時間
    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"Asia/Tokyo"]];
    dStr = [dateFormatter stringFromDate:[NSDate date]];
    
    NSLog(@"時區:%@ 當地時間:%@",[[dateFormatter timeZone] name], dStr);    
 

可以看到,NSDateFormatter根據時區設置,將時間進行調整。 如果加上時區的前者調整,其實是和GTM的時間是一致的。

NSDateFormatter也僅僅是將時間按照不同時區的設置進行顯示,NSLog(@"GTM 時間:%@",[NSDate date]);是在GTM時區下顯示時間。因此如果你看到的時間比本地時區顯示的時間有差異,加了多少小時,或者減了多少小時。

這點,在所有的計算機系統中都是一樣的,包括linux ,windows,solaris,aix等等。

NSDateFormatter也可以將指定格式的字符串轉換爲NSDate。這是其他語言中常見的時間轉字符串,字符串轉時間的操作方法。在ios的objective-c開發中,使用NSDateFormatter類來實現。不過,這裏加了一點,時區。如果不加,就是系統默認值。

    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"Asia/Shanghai"]];
    
    NSDate *dateFormatted=[dateFormatter dateFromString:@"2013-07-09 12:00:00"];
    
    NSLog(@"GTM 時間:%@",dateFormatted);
    
    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"Asia/Tokyo"]];
    
     dateFormatted=[dateFormatter dateFromString:@"2013-07-09 12:00:00" ];
    
    NSLog(@"GTM 時間:%@",dateFormatted);
    
    [dateFormatter setTimeZone:[NSTimeZone timeZoneWithName:@"GMT"]];
    
    dateFormatted=[dateFormatter dateFromString:@"2013-07-09 12:00:00"];
    
    NSLog(@"GTM 時間:%@",dateFormatted);

    
    

接着講NSCalendar。

NSCalendar是ios中的一個保存日曆數據的對象,其中也有時區設置,道理和NSDate一樣的。NSCalendar可以將NSDate對象在日曆中是一些屬性特徵顯示出來。NSCalendar根據設置的時區進行計算,將NSDate對象是一年中的第幾周,一個月中的第幾周等等計算出來。

NSCalendar還涉及到一個類NSDateComponents,兩者結合,可以將某些屬性拆分出來,也可以通過它來設置NSDate,也可以實現NSDate的加減和比較運算。

NSDateComponents也可以設置時區,設置年月日時分秒。

NSCalendar *localCalendar= [NSCalendar currentCalendar];
    
unsigned unitFlags = NSTimeZoneCalendarUnit|NSYearCalendarUnit | NSMonthCalendarUnit |NSDayCalendarUnit|NSHourCalendarUnit|NSMinuteCalendarUnit|NSSecondCalendarUnit;

unitFlags是一個設置,表示NSDateComponents會保存那些屬性,一般是時分秒天月年等等,還有星期幾,哪個季度,哪個月度,這裏將時區也一併保存了。
    NSDateComponents *comps = [localCalendar components:unitFlags fromDate:[NSDate date]];
    

    NSLog(@"時區:%@ hour is %d",[[comps timeZone] name] ,comps.hour);


同樣,也可以通過NSDateComponents設置得到一個NSDate對象。
    
    [comps setTimeZone:[NSTimeZone timeZoneWithName:@"Asia/Tokyo"]];
    
    [comps setSecond:00];
    [comps setMinute:00];
    [comps setHour:12];
    
    [comps setDay:9];
    [comps setMonth:7];
    [comps setYear:2013];
    
    NSLog(@"時區:%@ hour is %d",[[comps timeZone] name] ,comps.hour);
    
    NSDate *compsDate=[localCalendar dateFromComponents:comps];
    
    NSLog(@"GTM 時間:%@",compsDate);
    
    

總之,理解透了,也就這麼回事。將時區理解成日期時間的另一個屬性。像大陸的下午兩點和美國的下午兩點,不是一個時間,因爲還有時區這個前提條件存在。


測試結果如下:

2013-07-09 15:16:38.006 demo[14267:13d03] test begin.....................
2013-07-09 15:16:38.007 demo[14267:13d03] GTM 時間:2013-07-09 07:16:38 +0000
2013-07-09 15:16:38.007 demo[14267:13d03] [[NSTimeZone localTimeZone] name] is Asia/Shanghai
2013-07-09 15:16:38.008 demo[14267:13d03] 時區:Asia/Shanghai 當地時間:2013-07-9 15:16:38
2013-07-09 15:16:38.008 demo[14267:13d03] 時區:GMT 當地時間:2013-07-9 07:16:38
2013-07-09 15:16:38.009 demo[14267:13d03] GTM 時間:2012-07-09 04:00:00 +0000
2013-07-09 15:16:38.009 demo[14267:13d03] GTM 時間:2012-07-09 03:00:00 +0000
2013-07-09 15:16:38.009 demo[14267:13d03] GTM 時間:2012-07-09 12:00:00 +0000
2013-07-09 15:16:38.010 demo[14267:13d03] the end.....................
2013-07-09 15:16:38.010 demo[14267:13d03] ...............................
2013-07-09 15:16:38.010 demo[14267:13d03] test begin.....................
2013-07-09 15:16:38.010 demo[14267:13d03] 時區:Asia/Shanghai hour is 15
2013-07-09 15:16:38.011 demo[14267:13d03] 時區:Asia/Tokyo hour is 12
2013-07-09 15:16:38.011 demo[14267:13d03] GTM 時間:2013-07-09 03:00:00 +0000
2013-07-09 15:16:38.011 demo[14267:13d03] the end.....................

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章