var x = new Array(); x["foo"] = "bar"; x["bar"] = "baz"; x.length This script produces: "0" Shouldn't associative arrays have a length attribute which reports the number of keys contained in the array's hash table?
From the ECMA3 spec: 15.4 Array Objects Array objects give special treatment to a certain class of property names. A property name P (in the form of a string value) is an array index if and only if ToString(ToUint32(P)) is equal to P and ToUint32(P) is not equal to 2 32 -1. Every Array object has a length property whose value is always a nonnegative integer less than 2 32 . The value of the length property is numerically greater than the name of every property whose name is an array index; whenever a property of an Array object is created or changed, other properties are adjusted as necessary to maintain this invariant. Specifically, whenever a property is added whose name is an array index, the length property is changed, if necessary, to be one more than the numeric value of that array index; and whenever the length property is changed, every property whose name is an array index whose value is not smaller than the new length is automatically deleted. This constraint applies only to properties of the Array object itself and is unaffected by length or array index properties that may be inherited from its prototype.
Have to mark this one as invalid. According to the spec, the length property of an Array object counts the number of properties whose name P is an "array index" as defined by the spec. This means in particular, P == ToString(ToUint32(P)) In short, P must be numerical. So, for example, if we do this: var x = new Array(); x['0'] = 'bar'; x = 'baz'; x['a'] = 'foo'; x.length; the output will be 2, not 3, because both '0' and 1 are ECMA "array indices", but 'a' is not.
Verifying Phil's analysis. I'm afraid I can think of no better way of counting the properties of a generic object - and the code snippet you show runs afoul of properties in the prototype, too. You need : for (x in a) if (a.hasOwnProperty(x)) counter++; bleagh!
See bug 57048 for more info on this -