Valor inesperado do NSDate

Estou tentando armazenar um horário em uma data. Neste caso, 1,5 segundos. Eu guardo a hora na data assim:

NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init]; [dateFormatter setDateFormat:@"mm:ss.SS"]; [dateFormatter setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0.0]]; NSDate *date1 = [dateFormatter dateFromString:@"00:01.50"]; 

Mas se eu olhar na área de debugging, posso ver que o valor de date1 foi definido como:

 date1 = (NSDate *) 0x1dd32b30 2000-01-01 01:00:01 CET 

Alguém poderia me dizer por que isso está acontecendo?

Porque há uma massa de questões relacionadas ao NSDate em SO e todos eles têm a mesma sombra, eu vou te dar uma resposta mais longa, provavelmente isso pode ser encaminhado de outras questões.

A. Existe um mal-entendido comum, o que é uma data: Uma data é um ponto na linha do tempo. Não lida com horas ou minutos, não lida com dias, meses, anos, não lida com fusos horários.

É um ponto em uma linha do tempo. Período.

(E internamente é representado por um número de ponto flutuante. Isso é uma surpresa?)

B. Existe outro equívoco comum, o que é uma data: Duas datas, portanto, pontos em uma linha do tempo, são iguais, se tiverem o mesmo valor. Isso não significa que eles tenham a mesma representação. Duas vezes podem ser iguais, até mesmo sua representação é completamente diferente. (Isto é, o que aconteceu com você.) Para uma comparação, não importa, qual fuso horário está em uso, esperado, $ o que quer que seja. Para uma comparação não importa, qual calendar está em uso, esperado ou $ qualquer. Se for 11:11 em Colônia, Alemanha (UTC + 1) é 10:11 em Londres, Inglaterra (UTC + 0). Esta é a mesma hora.

Uma data é anterior se estiver na linha do tempo antes de outra data.

C. Então, quais são essas coisas engraçadas como dia, mês, fuso horário e assim por diante? Desde que fora de um episódio de Star Trek, um tempo como 26.182.382.303,127373 seria difícil de entender e lidar, os seres humanos começaram a dar pontos na linha do tempo nomes engraçados. Essas representações não são a data. Eles são representações da data. É o mesmo problema com os números. Você não esta piada?

“Existem 10 tipos de pessoas: Aqueles que entendem números binários e aqueles que não entendem.”

O espírito da piada é que 10 pode ser o valor de dez, se estiver escrito em notação decimal ou pode ser o valor de dois, escrito em notação binária. Ninguém pode dizer que valor “10” denota a menos que ele conheça o sistema numeral que é usado para a representação. A maioria das pessoas assume que está em um sistema decimal, então “10” significa dez. Esta é uma convenção popular. E isso funciona bem, já que quase todo o mundo adotou essa convenção. Mas: “10” pode denotar dois valores diferentes. E o contrário, também: O mesmo valor pode ser escrito com diferentes “strings”: 10 em notação decimal é igual a 1010 em notação binária (e é igual a “2 + 8”, sqrt (100), … Isso é , porque é permitido escrever = entre eles.)

Unfortunaly (não, não realmente, o tempo tem que trabalhar localmente de uma maneira fácil) pelo tempo não existe uma convenção mundial. Se alguém escreve “11:11” você simplesmente não pode dizer, a que horas (lembre-se, é um ponto na linha do tempo) se entende. Provavelmente, a pessoa diz implicitamente que este é o momento em seu sistema de calendar em seu fuso horário. Mas então você tem que saber, em que local do mundo ele está dizendo isso. Levando dia, mês e assim por diante, você provavelmente tem que saber, qual é a religião dele, porque mesmo em um país pessoas de religiões diferentes usam calendars diferentes.

Como não existe uma convenção mundial comum, por um lado, e o Mac OS está sendo executado em sistemas de computadores em todo o mundo, você não pode presumir que um tempo impresso seja gravado em uma anotação que você espera.

Portanto, é completamente, eh, não muito inteligente comparar com datas por string. Você não compara datas, você compara seqüências de caracteres.

Antes de comparar uma hora (incluindo a data), você precisa transformar a representação em uma hora para a hora “real”. Você tem que adicionar informações sobre o calendar, a representação está escrita e o fuso horário (que está incluído no calendar no Cocoa).

No Cocoa você usa instâncias de NSDateFormatter, NSCalendar, NSDateComponents para fazer este trabalho. Se você deixar o NSDateFormatter transformar uma representação em uma hora e vice-versa, será necessário definir o calendar. (NSDateFormatter assume que o calendar local é escolhido, se você não definir um.) É simplesmente impossível NSDateFormatter fazer qualquer trabalho de transformação, se ele não souber qual calendar usar. E isso é simplesmente impossível para você.

Então você pode fazer alguns cálculos com ele, a data, a hora, a instância do NSDate, incluindo comparação e pelo menos você tem que transformá-lo de volta em uma representação legível usando um calendar.

O que você consegue e deixa você pensar, que é uma hora errada, é simplesmente a hora certa, mas em uma representação que você não esperava. (-description sempre entrega UTC + 0).

Tentar NSLog na data retornará a data apenas no formato GMT. Portanto, se você quiser verificar se está obtendo a hora ou a data correta, converta data em string e NSLog.

 NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init]; [dateFormatter setDateFormat:@"mm:ss.SS"]; [dateFormatter setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0.0]]; NSDate *date1 = [dateFormatter dateFromString:@"00:01.50"]; NSString *dateString = [dateFormatter stringFromDate:date1]; NSlog(@"%@",dateString);