Si cela aide, pensez aux températures. Ils peuvent être exprimés en Fahrenheit, Celsius ou Kelvin. Mais l'information exprimée (le mouvement moyen des molécules) n'a pas d'unité intrinsèque, bien qu'elle ne soit significative pour nous que lorsqu'elle est exprimée dans une unité.
logiciel a évolué le
7
@DaveDeLong NSDate a un fuseau horaire. À partir de la référence de classe NSDate: "Cette méthode renvoie une valeur d'heure relative à une date de référence absolue - le premier instant du 1er janvier 2001, GMT." Notez la référence claire et spécifique à GMT.
Murray Sagal
3
Je ne suis pas d'accord. NSDate n'a PAS de fuseau horaire. Pour spécifier le fuseau horaire du NSDate, vous utilisez un objet NSCalendar ou un objet NSDateFormatter. Si vous créez un NSDate à partir d'une chaîne pour laquelle aucun fuseau horaire n'est spécifié, le NSDate supposera que la chaîne est à l'heure GMT.
Rickster
1
@MurraySagal Ce n'est pas parce que cette méthode particulière renvoie une valeur d'heure relative à une date dans un fuseau horaire spécifique que NSDate modélise une date comme étant relative à un fuseau horaire.
eremzeit
Réponses:
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
il vaut probablement la peine de mentionner que vous pouvez également utiliser le formateur pour lire les dates à partir de chaînes
slf
34
@DaveDeLong c'est très bien si vous affichez simplement la date sous forme de chaîne. Mais il existe des raisons parfaitement valables pour effectuer des conversions de fuseau horaire sur une date. Par exemple, si vous souhaitez définir la date par défaut sur un UIDatePicker à l'aide de setDate :. Les dates renvoyées par les services Web sont souvent UTC, mais représentent un événement dans le fuseau horaire local de l'utilisateur, comme une liste télévisée. Passer une date non convertie affichera l'heure incorrecte dans le sélecteur.
Christopher Pickslay
5
@GlennMaynard Je ne suis pas d'accord. L'essence de cette réponse est qu'aucune conversion en NSDateobjet n'est nécessaire, ce qui est correct. La conversion en fuseau horaire se produit lorsque la date est formatée, pas lors de sa création, car les dates n'ont pas de fuseau horaire.
Dave DeLong
1
@GlennMaynard ... sauf que NSCalendarDatec'est obsolète.
EDIT Quand j'ai écrit ceci, je ne savais pas que je devrais utiliser un datformatter qui est probablement une meilleure approche, alors vérifiez aussi slfla réponse de.
J'ai un webservice qui renvoie les dates en UTC. J'utilise toLocalTimepour le convertir en heure locale et toGlobalTimepour le reconvertir si nécessaire.
Ne fais pas ça. Les NSDates sont toujours en UTC. Cela ne fait que confondre le problème.
JeremyP
13
Cela peut être très utile pour le cas du "webservice" mentionné ci-dessus. Disons que vous avez un serveur qui stocke les événements en UTC et que le client souhaite demander tous les événements qui se sont produits aujourd'hui. Pour ce faire, le client doit obtenir la date actuelle (UTC / GMT), puis la décaler de son décalage de fuseau horaire avant de l'envoyer au serveur.
Taylor Lafrinere
@JeremyP Il serait plus exact de dire que les NSDates sont toujours en GMT. À partir de la référence de classe NSDate: "Cette méthode renvoie une valeur d'heure relative à une date de référence absolue - le premier instant du 1er janvier 2001, GMT." Notez la référence claire et spécifique à GMT. Il existe une différence technique entre GMT et UTC, mais cela n'a généralement pas de rapport avec les solutions que la plupart des gens recherchent.
Cette réponse semble plus portable. La réponse ci-dessous suppose que le fuseau horaire est fixé au moment de l'exécution, tandis que la réponse ci-dessus dérive le fuseau horaire de la plate-forme.
bleeckerj
9
Très utile. Un ajout secondsFromGMTForDatedoit être utilisé si vous souhaitez tenir compte de l'heure d'été. Voir Apple Docs
Sergey Markelov
1
Cela ne prend pas en compte les modifications DST.
lkraider
36
Swift 3+ : UTC vers Local et Local vers 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)}}
Très bonne réponse! Cela saisira la date actuelle. Une adaptation de ce qui utilise une chaîne de date serait de remplacer [NSDate date]par [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
Comme personne ne semblait utiliser NSDateComponents, j'ai pensé que j'en lancerais un ... Dans cette version, no NSDateFormatterest utilisé, donc pas d'analyse de chaîne, et NSDaten'est pas utilisé pour représenter le temps en dehors de GMT (UTC). L'original NSDateest dans la variable 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_anotherCalendarpourrait être NSCalendarIdentifierGregorianou tout autre calendrier. Le NSStringpermis i_anotherTimeZonepeut être acquis avec [NSTimeZone knownTimeZoneNames], mais anotherCalendar.timeZonepourrait être [NSTimeZone defaultTimeZone]ou [NSTimeZone localTimeZone]ou[NSTimeZone systemTimeZone] tout à fait.
Il tient en fait anotherComponentsl'heure dans le nouveau fuseau horaire. Vous remarquerez qu'il anotherDateest égal à i_date, car il contient l'heure GMT (UTC).
Réponses:
Tableau des paramètres de chaîne de formatage:
https://waracle.com/iphone-nsdateformatter-date-formatting-table/
Si les performances sont une priorité, vous pouvez envisager d'utiliser
strftime
https://developer.apple.com/legacy/library/documentation/Darwin/Reference/ManPages/man3/strftime.3.htmlla source
NSDate
objet n'est nécessaire, ce qui est correct. La conversion en fuseau horaire se produit lorsque la date est formatée, pas lors de sa création, car les dates n'ont pas de fuseau horaire.NSCalendarDate
c'est obsolète.EDIT Quand j'ai écrit ceci, je ne savais pas que je devrais utiliser un datformatter qui est probablement une meilleure approche, alors vérifiez aussi
slf
la réponse de.J'ai un webservice qui renvoie les dates en UTC. J'utilise
toLocalTime
pour le convertir en heure locale ettoGlobalTime
pour le reconvertir si nécessaire.C'est de là que j'ai obtenu ma réponse:
https://agilewarrior.wordpress.com/2012/06/27/how-to-convert-nsdate-to-different-time-zones/
la source
La méthode la plus simple que j'ai trouvée est la suivante:
la source
secondsFromGMTForDate
doit être utilisé si vous souhaitez tenir compte de l'heure d'été. Voir Apple DocsSwift 3+ : UTC vers Local et Local vers UTC
la source
Si vous voulez une date et une heure locales. Essayez ce code: -
la source
[NSDate date]
par[NSDate dateWithNaturalLanguageString:sMyDateString]
.Convertissez votre date UTC en date locale
Utilisez comme ça
la source
Ici, l'entrée est une chaîne currentUTCTime (au format 30/08/2012 11:11) convertit l'heure d'entrée en GMT en heure de zone définie par le système
la source
la source
Convertissez la date du calendrier UTC en une date avec la NSTimeZone locale appropriée .
la source
J'écris cette méthode pour convertir la date et l'heure dans notre LocalTimeZone
-Here (NSString *) paramètre TimeZone est un fuseau horaire du serveur
la source
Comme personne ne semblait utiliser
NSDateComponents
, j'ai pensé que j'en lancerais un ... Dans cette version, noNSDateFormatter
est utilisé, donc pas d'analyse de chaîne, etNSDate
n'est pas utilisé pour représenter le temps en dehors de GMT (UTC). L'originalNSDate
est dans la variablei_date
.i_anotherCalendar
pourrait êtreNSCalendarIdentifierGregorian
ou tout autre calendrier. LeNSString
permisi_anotherTimeZone
peut être acquis avec[NSTimeZone knownTimeZoneNames]
, maisanotherCalendar.timeZone
pourrait être[NSTimeZone defaultTimeZone]
ou[NSTimeZone localTimeZone]
ou[NSTimeZone systemTimeZone]
tout à fait.Il tient en fait
anotherComponents
l'heure dans le nouveau fuseau horaire. Vous remarquerez qu'ilanotherDate
est égal ài_date
, car il contient l'heure GMT (UTC).la source
Vous pouvez essayer celui-ci:
la source
Convertissez l'heure UTC en fuseau horaire actuel.
fonction d'appel
Fonction
la source