Unexpected value from NSDate

Because there is a mass of question related to NSDate on SO and they all have the same shade, I will give you a longer answer, probably this can be referred from other questions.

A. There is a common misunderstanding, what a date is: A date is a point on timeline. It does not deal with hours or minutes, it does not deal with days, month, years, it does not deal with timezones.

It is a point on a timeline. Period.

(And internally it is represented by an floating-point number. Is that a surprise?)

B. There is another common misunderstanding, what a date is: Two dates, therefore points on a timeline, are equal, if the have the same value. This does not mean, that they have the same representation. Two times can be equal, even their representation is completly different. (This is, what happened to you.) For a comparison it does not matter, which timezone is in use, expected, $whatever. For a comparison is does not matter, which calendar is in use, expected or $whatever. If it is 11:11 in Cologne, Germany (UTC+1) it is 10:11 in London, England (UTC+0). This is the same time.

A date is earlier if it is on the timeline ahead of another date.

C. So what are these funny things like days, month, timezones and so on?
Since outside a star trek episode a time like 26,182,382,303.127373 would be difficult to understand and to handle, human beings began to give points on the timeline funny names. This representations are not the date. They are representations of the date. It is the same problem with numbers. Do you no this joke?

“There are 10 kind of people: Those, who understand binary numbers and those who doesn’t.”

The spirit of the joke is, that 10 can be the value of ten, if it is written in decimal notation or it can be the value of two, written in binary notation. Nobody can say, what value “10” denotes unless he knows the numeral system which is used for the representation. Most people assume, that it is in a decimal system, so “10” means ten. This is a popular convention. And this works fine since nearly all over the world adopted that convention. But: “10” can denote two different values. And the other way around, too: The same value can be written with different “strings”: 10 in decimal notation is equal to 1010 in binary notation (and is equal to “2+8”, sqrt(100), … That is, why it is allowed to write = between them.)

Unfortunaly (no, not really, time has to work locally in an easy way) for time there is no world-wide convention. If somebody writes “11:11” you simply cannot say, what time (remember, it is a point on the timeline) is meant. Probably the person implicitly says, that this is the time in his calendaric system in his timezone. But then you have to know, at which location on the world he is saying that. Taking day, month and so on in account, you probably have to know, what is his religion, because even in one country people of different religions uses different calendars.

Since there is no common world-wide convention on one hand and Mac OS is running on computer systems world-wide, you cannot assume, that a time printed out is written in a notation you expect.

Therefore it is completly, eh, not very intelligent to compare to dates by string. You do not compare dates, you compare strings.

Before you compare a time (including date) you have to transform the representation to a time to the “real” time. You have to add information about the calendar, the representation is written in and the timezone (which is included in the calendar in Cocoa).

In Cocoa you use instances of NSDateFormatter, NSCalendar, NSDateComponents to do this job. If you let NSDateFormatter transform a representation to a time and vice versa, you have to set the calendar. (NSDateFormatter assumes, that the local calendar is choosen, if you do not set one.) It is simply impossible to NSDateFormatter to do any transformation work, if it does not know which calendar to use. And it is simply impossible for you.

Then you can do some calculations with it, the date, the time, the instance of NSDate, including comparison and at least you have to transform it back into a human-readable representation using a calendar.

What you get and let you think, that it is a wrong time, is simply the correct time but in a represenatation you did not expect. (-description always delivers UTC+0).

Leave a Comment