Jeśli to pomoże, pomyśl o temperaturach. Można je wyrazić w stopniach Fahrenheita, Celsjusza lub Kelvina. Ale wyrażana informacja (średni ruch cząsteczek) nie ma wewnętrznej jednostki, chociaż ma dla nas znaczenie tylko wtedy, gdy jest wyrażona w jakiejś jednostce.
oprogramowanie ewoluowało
7
@DaveDeLong NSDate ma strefę czasową. Z odwołania do klasy NSDate: „Ta metoda zwraca wartość czasu w stosunku do bezwzględnej daty odniesienia - pierwsza chwila 1 stycznia 2001 r. GMT”. Zwróć uwagę na jasne i konkretne odniesienie do GMT.
Murray Sagal
3
Nie zgadzam się. NSDate NIE ma strefy czasowej. Aby określić strefę czasową dla NSDate, użyj obiektu NSCalendar lub obiektu NSDateFormatter. Jeśli utworzysz NSDate z ciągu, który nie ma określonej strefy czasowej, wówczas NSDate przyjmie, że ciąg jest w czasie GMT.
Rickster
1
@MurraySagal Tylko dlatego, że ta konkretna metoda zwraca wartość czasu w odniesieniu do daty w określonej strefie czasowej, nie oznacza to, że NSDate modeluje datę jako relatywną do strefy czasowej.
eremzeit
Odpowiedzi:
139
NSTimeInterval seconds;// assume this existsNSDate* ts_utc =[NSDate dateWithTimeIntervalSince1970:seconds];NSDateFormatter* df_utc =[[[NSDateFormatter alloc] init] autorelease];[df_utc setTimeZone:[NSTimeZone timeZoneWithName:@"UTC"]];[df_utc setDateFormat:@"yyyy.MM.dd G 'at' HH:mm:ss zzz"];NSDateFormatter* df_local =[[[NSDateFormatter alloc] init] autorelease];[df_local setTimeZone:[NSTimeZone timeZoneWithName:@"EST"]];[df_local setDateFormat:@"yyyy.MM.dd G 'at' HH:mm:ss zzz"];NSString* ts_utc_string =[df_utc stringFromDate:ts_utc];NSString* ts_local_string =[df_local stringFromDate:ts_utc];// you can also use NSDateFormatter dateFromString to go the opposite way
prawdopodobnie warto wspomnieć, że możesz użyć programu formatującego do odczytania dat również z łańcuchów
slf
34
@DaveDeLong to wszystko dobrze i dobrze, jeśli wyświetlasz tylko datę jako ciąg. Istnieją jednak całkowicie uzasadnione powody, dla których warto przeprowadzić konwersję strefy czasowej na randkę. Na przykład, jeśli chcesz ustawić domyślną datę w UIDatePicker za pomocą setDate :. Daty zwracane przez usługi internetowe są często podawane w czasie UTC, ale reprezentują wydarzenie w lokalnej strefie czasowej użytkownika, takie jak program telewizyjny. Przekazanie nieprzekształconej daty spowoduje wyświetlenie nieprawidłowego czasu w selektorze.
Christopher Pickslay
5
@GlennMaynard Nie zgadzam się. Istota tej odpowiedzi polega na tym, że żadna konwersja do NSDateprzedmiotu nie jest konieczna, co jest poprawne. Konwersja do strefy czasowej następuje po sformatowaniu daty, a nie po jej utworzeniu, ponieważ daty nie mają stref czasowych.
Dave DeLong,
1
@GlennMaynard ... z wyjątkiem tego, że NSCalendarDatejest przestarzały.
EDYTUJ Kiedy to pisałem, nie wiedziałem, że powinienem użyć formatu daty, który jest prawdopodobnie lepszym podejściem, więc sprawdź slfteż odpowiedź.
Mam usługę sieciową, która zwraca daty w UTC. Używam, toLocalTimeaby przekonwertować go na czas lokalny i toGlobalTimew razie potrzeby przekonwertować z powrotem.
Nie rób tego. NSDates są zawsze w UTC. To tylko myli sprawę.
JeremyP
13
Może to być bardzo przydatne w przypadku „usługi sieciowej” opisanej powyżej. Powiedzmy, że masz serwer, który przechowuje wydarzenia w UTC, a klient chce zapytać o wszystkie wydarzenia, które miały miejsce dzisiaj. Aby to zrobić, klient musi uzyskać aktualną datę (UTC / GMT), a następnie przesunąć ją zgodnie z przesunięciem strefy czasowej przed wysłaniem jej na serwer.
Taylor Lafrinere
@JeremyP Dokładniej byłoby powiedzieć, że NSDates są zawsze w GMT. Z odwołania do klasy NSDate: „Ta metoda zwraca wartość czasu w stosunku do bezwzględnej daty odniesienia - pierwsza chwila 1 stycznia 2001 r. GMT”. Zwróć uwagę na jasne i konkretne odniesienie do GMT. Istnieje różnica techniczna między GMT i UTC, ale w większości przypadków nie ma to znaczenia dla rozwiązań, których szuka większość ludzi.
Ta odpowiedź wydaje się bardziej przenośna. Poniższa odpowiedź zakłada, że strefa czasowa jest ustalona w czasie wykonywania, podczas gdy powyższa odpowiedź pochodzi ze strefy czasowej z platformy.
bleeckerj
9
Bardzo pomocne. secondsFromGMTForDateNależy użyć jednego dodatku, jeśli chcesz uwzględnić czas letni. Zobacz Apple Docs
Sergey Markelov,
1
Nie uwzględnia to zmian czasu letniego.
lkraider
36
Swift 3+ : od UTC do lokalnego i od lokalnego do UTC
extension Date{// Convert UTC (or GMT) to local time
func toLocalTime()->Date{let timezone =TimeZone.current
let seconds =TimeInterval(timezone.secondsFromGMT(for:self))returnDate(timeInterval: seconds, since:self)}// Convert local time to UTC (or GMT)
func toGlobalTime()->Date{let timezone =TimeZone.current
let seconds =-TimeInterval(timezone.secondsFromGMT(for:self))returnDate(timeInterval: seconds, since:self)}}
Świetna odpowiedź! Spowoduje to pobranie aktualnej daty. Adaptacja ta, która wykorzystuje datę ciąg byłoby wymienić [NSDate date]z [NSDate dateWithNaturalLanguageString:sMyDateString].
//This is basic way to get time of any GMT time.NSDateFormatter*formatter =[[NSDateFormatter alloc] init];[formatter setDateFormat:@"hh:mm a"];// 09:30 AM[formatter setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:1]];// For GMT+1NSString*time =[formatter stringFromDate:[NSDate date]];// Current time
Ponieważ wydawało się NSDateComponents, że nikt nie używa , pomyślałem, że będę go używać ... W tej wersji nie NSDateFormatterjest używane, stąd nie ma analizowania ciągów i NSDatenie jest używane do reprezentowania czasu poza GMT (UTC). Oryginał NSDateznajduje się w zmiennej i_date.
NSCalendar*anotherCalendar =[[NSCalendar alloc] initWithCalendarIdentifier:i_anotherCalendar];
anotherCalendar.timeZone =[NSTimeZone timeZoneWithName:i_anotherTimeZone];NSDateComponents*anotherComponents =[anotherCalendar components:(NSCalendarUnitEra|NSCalendarUnitYear|NSCalendarUnitMonth|NSCalendarUnitDay|NSCalendarUnitHour|NSCalendarUnitMinute|NSCalendarUnitSecond|NSCalendarUnitNanosecond) fromDate:i_date];// The following is just for checking
anotherComponents.calendar = anotherCalendar;// anotherComponents.date is nil without thisNSDate*anotherDate = anotherComponents.date;
i_anotherCalendarmógłby być NSCalendarIdentifierGregorianlub jakikolwiek inny kalendarz. NSStringPozwoliło i_anotherTimeZonemogą być nabywane z [NSTimeZone knownTimeZoneNames], ale anotherCalendar.timeZonemoże być [NSTimeZone defaultTimeZone]albo [NSTimeZone localTimeZone]czy [NSTimeZone systemTimeZone]w ogóle.
W rzeczywistości anotherComponentsutrzymuje czas w nowej strefie czasowej. Zauważysz, że anotherDatejest równe i_date, ponieważ zawiera czas w GMT (UTC).
Odpowiedzi:
Tabela formatowania parametrów ciągu:
https://waracle.com/iphone-nsdateformatter-date-formatting-table/
Jeśli priorytetem jest wydajność, możesz rozważyć użycie
strftime
https://developer.apple.com/legacy/library/documentation/Darwin/Reference/ManPages/man3/strftime.3.htmlźródło
NSDate
przedmiotu nie jest konieczna, co jest poprawne. Konwersja do strefy czasowej następuje po sformatowaniu daty, a nie po jej utworzeniu, ponieważ daty nie mają stref czasowych.NSCalendarDate
jest przestarzały.EDYTUJ Kiedy to pisałem, nie wiedziałem, że powinienem użyć formatu daty, który jest prawdopodobnie lepszym podejściem, więc sprawdź
slf
też odpowiedź.Mam usługę sieciową, która zwraca daty w UTC. Używam,
toLocalTime
aby przekonwertować go na czas lokalny itoGlobalTime
w razie potrzeby przekonwertować z powrotem.Stąd otrzymałem odpowiedź:
https://agilewarrior.wordpress.com/2012/06/27/how-to-convert-nsdate-to-different-time-zones/
źródło
Najłatwiejsza metoda, jaką znalazłem, to:
źródło
secondsFromGMTForDate
Należy użyć jednego dodatku, jeśli chcesz uwzględnić czas letni. Zobacz Apple DocsSwift 3+ : od UTC do lokalnego i od lokalnego do UTC
źródło
Jeśli chcesz lokalną datę i godzinę. Wypróbuj ten kod: -
źródło
[NSDate date]
z[NSDate dateWithNaturalLanguageString:sMyDateString]
.Konwertuj swoją datę UTC na datę lokalną
Użyj w ten sposób
źródło
Tutaj dane wejściowe to ciąg currentUTCTime (w formacie 08/30/2012 11:11) konwertuje czas wejściowy w GMT na ustawiony przez system czas strefy
źródło
źródło
Konwertuj datę z kalendarza UTC na datę z odpowiednią lokalną strefą NSTimeZone .
źródło
Piszę tę metodę, aby przekonwertować datę i godzinę na naszą LocalTimeZone
-Here (NSString *) Parametr TimeZone to strefa czasowa serwera
źródło
Ponieważ wydawało się
NSDateComponents
, że nikt nie używa , pomyślałem, że będę go używać ... W tej wersji nieNSDateFormatter
jest używane, stąd nie ma analizowania ciągów iNSDate
nie jest używane do reprezentowania czasu poza GMT (UTC). OryginałNSDate
znajduje się w zmienneji_date
.i_anotherCalendar
mógłby byćNSCalendarIdentifierGregorian
lub jakikolwiek inny kalendarz.NSString
Pozwoliłoi_anotherTimeZone
mogą być nabywane z[NSTimeZone knownTimeZoneNames]
, aleanotherCalendar.timeZone
może być[NSTimeZone defaultTimeZone]
albo[NSTimeZone localTimeZone]
czy[NSTimeZone systemTimeZone]
w ogóle.W rzeczywistości
anotherComponents
utrzymuje czas w nowej strefie czasowej. Zauważysz, żeanotherDate
jest równei_date
, ponieważ zawiera czas w GMT (UTC).źródło
Możesz spróbować tego:
źródło
Konwertuj czas UTC na aktualną strefę czasową.
funkcja wywołania
Funkcjonować
źródło