Thursday 10 September 2009 — This is 15 years old. Be careful.
My son Max is taking a computer class in high school, and described a class exercise involving a deck of cards numbered 0 to 51. I asked him if there was any discussion in class about why it wasn’t 1 to 52. He said the teacher told them that if they learned C++, they’d understand why it started from zero.
I guess the teacher meant pointer arithmetic makes it obvious, but I remembered a more scholarly exposition: Edsger Dijkstra wrote a brief paper called Why Numbering Should Start at Zero. He lays out a mathematical explanation that has nothing directly to do with pointers.
I’m impressed by Dijkstra because of his methodical approach to even the seemingly most trivial detail of computing. He was willing to stop, think through, and explain why something should be done a certain way, no matter how small.
Earlier today over lunch, we discussed the amazing foresight of the AT&T engineers who laid out the North American area codes. We marvelled at the care they took with designing a solution to a problem that wouldn’t hit for a decade or so. How often do we see that kind of care and attention to detail in day-to-day work?
Both examples made me stop and admire true professionals, engineers building carefully, making sure to get it right no matter how far off the consequences. Thanks, guys. We should each try to channel your spirit in our own work.
Comments
You're absolutely right though, some things in everyday life which are taken for granted actually took someone to really sit down and work through a problem to get it right. Others people don't even see, Google's GFS as an example and simply use the product without any care of understanding about just how incredible the GFS service is.
I might be inclined to write rather than in Python.
Using range might give some tiny performance penalty compared to latter. Hence if it's performance you are after you might write a code generator to replace it with latter. But if you are after performance you won't be writing this kind of code in Python anyway. :)
[1] Writing < and = together (no whitespace) seems to break your preview and possibly the post text (not tested) by cutting it right there.
One consideration he doesn't address is the significant cultural preference, if you will, towards naming indices by the positive integers. Even as a C++ programmer long past the stage of uncomfortableness with 0-based indexing, in my head I still say "the first element," "the second item," "the third thing," and so on.
There is also the issue of exactly what operations on intervals should be optimized. The interval [A, B) makes it "easy" to determine the length of the interval and the first element but not as easy to determine the maximum element of the interval. (A, B] makes it easy to determine the length and the maximum element, but not the minimum element. And [A, B] makes the min and max easy, but not the length. Finally, the half-open intervals are easier to add; another point in their favor.
Even if we grant his having established the mathematical superiority of closed/open intervals starting at 0, the real question then becomes: does the mathematical attractiveness outweigh the impedance mismatch with entrenched habits?
It would be nice and simple to categorically say "yes," but it's not clear that that's true. Off-by-one pointer errors in C due to the above-mentioned disconnect, for example, have had measurable economic impact.
Dijkstra uses the 0..n-1 for his page numbering in this note. Dogma has apparently triumphed over elegance and convention here. Wouldn't this be even more confusing if the total number of pages were also displayed? The final page would be labelled "Page 2 of 3". Now that would cause some real problems in an examination!
the beginning of his paper. He says that 'A <= i < B' and 'A < i <= B' are better because they:
So, 9/2=3, 8/2=2, 6/1=3, 4/1=2, 1/1=0.5 and most importantly n/0=n.
Now, I just have to persuade everyone to overturn millennium of mathematical convention just so I don't have to watch for divide by zero exceptions.
Add a comment: