Aesthetic argument for 0-based indices: or, "Why Lua is Just Wrong"
Most programming languages have a data structure called an “array”. An array is a sequential list of items—like a numbered list—and when you want an item you ask for it by number.
Most ‘good’ programming languages (e.g. C, JavaScript, Ruby) call the first element in the array “item number 0”, the second item in the array “item number 1”, and so on. This makes sense to the computer, because if you are storing an array in memory and each item in the array is n bytes long, the the first item in the array is at memory address array_address + 0*n
, the second item in the array is at array_address + 1*n
, and so on.
For humans, however, this nomenclature is hard. “If I want the 15th item in the list, I have to ask for item number 14? Whaaa?”
Some humans have so much trouble with this that they created otherwise-good programming languages and chose to call the first element in the array item number 1. Here’s an aesthetic argument for why using 0-based indices makes more sense.
Following is a list of 100 numbers, arranged in a grid:
01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 |
21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 |
31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 |
41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 |
51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 |
61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 |
71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 |
81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 |
91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 |
Now, let’s highlight all the numbers that have an ‘8’ in them:
01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 |
21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 |
31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 |
41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 |
51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 |
61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 |
71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 |
81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 |
91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 |
Ugh. Not only is the line broken, but the vertical is two columns away from the right while the horizontal is only one row from the bottom. Displeasing, at best. However, if we start numbering from 0:
00 | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 |
10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 |
20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 |
30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 |
40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 |
50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 |
60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 |
70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 |
80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 |
90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 |
Pick any digit and highlight the rows and columns with that digit in it.
- When using a 0-based grid the highlighting is always attractive and symmetrical.
- When using a 1-based grid the highlighting is either ugly or (in the case of
0
) inconsistent.
For good measure, here’s a non-aesthetic, programmer-centric argument. Compare the following two scripts that repeatedly loop through the items in an array, and tell me which you’d prefer to type:
// JavaScript, using 0-based array indices var a = ['a','b','c','d','e']; // Array of 5 items var size = a.length; // 5 for (var i=0;i<1000;i++){ var item = a[ i % size ]; // Modulus division yields 0,1,2,3,4,0,1,2,3,4,0,1,… }
# Lua, using 1-based array indices local a = {'a','b','c','d','e'} # Table of 5 items local size = table.maxn(a) # 5 for i=1,1000 do local item = a[ (i-1) % size + 1 ] # Shift for modulus end