By not inheriting from Object.prototype
with Object.create(null)
, your object no longer has the methods on the object prototype. So the obvious question is, what are the methods on that prototype, and do you need them?
The methods are:
hasOwnProperty
isPrototypeOf
propertyIsEnumerable
toString
/toLocaleString
valueOf
hasOwnProperty
seems kind of useless because if there is no prototype, all properties on the created object are by definition own properties. However, it's conceivable that some library or other piece of code might be iterating over the object's properties with for...in
and using the if (o.hasOwnProperty(key))
idiom. It is probably too much to hope for that it would use the more correct Object.prototype.hasOwnProperty.call(o, key)
. Such code would now fail. Or, you might be creating a sub-object with the created object as prototype, and be interested in knowing whether a property is an own property of the sub-object or comes from the prototype.
isPrototypeOf
might or might not be useful if you plan to use the created object as the prototype for other objects, and for some reason want to check if the created object is or is not in the prototype chain of such other objects.
propertyIsEnumerable
would not be used too much, but then again, we cannot predict what other code in the system is going to do. If it tries to call this method on the created object, or any objects created with it as a prototype, it will fail.
The same holds for toString
. Who knows who might try to call it on your created object? For instance, some libraries might try to test a value's type by doing a toString
and seeing if the result is "[object Object]"
. Hopefully they do a safe Object.prototype.toString.call(o)
, but...
valueOf
is rarely used explicitly, but is called by the engine if it needs to coerce the object to a primitive. If it is missing, the code could break:
> o2 = Object.create(null)
> o2 + 1
Uncaught TypeError: Cannot convert object to primitive value
Of course, there is also the possibility that someone has added methods to the Object
prototype, in which case Object.create({})
will pick them up. Probably you don't want or need them. On the other hand, they are most likely harmless.
Given all of this, it seems that Object.create(null)
should be limited to specific cases where it is provable that none of the above issues could occur. For instance, where the object is never even passed outside its local context, or is never going to be used as a prototype for another object. Even in that case, the performance advantage will be very small, or even zero.
I'm interested to know if others use Object.create(null)
? Is it SOP in JavaScript land?
I don't think it could be called SOP.