What are the benefits and dangers of adding methods to Object.prototype in Javascript?
I know this was a contentious issue five years ago, but I'm wondering if things have changed for today's JavaScript. Are there any real world examples of a major modern library being incompatible with extending Object.pr开发者_运维知识库ototype
?
I'm not interested in hypothetical "someone may write bad for in
iteration code in a library that you want to use, maybe, in the future, and then you might get a weird bug"
Are there any real world examples of a major modern library being incompatible with extending Object.prototype?
Yes, I remember problems with jQuery, -which is one of the less intrusive libraries- for example:
- I tried to prototype a length() method to Object and broke jQuery – how?
Another case that I remember is that someone added a load
function to the Object.prototype
object, and it caused problems with the $().load
event:
// DON'T DO THIS ! :)
Object.prototype.load = function () {};
$(window).load(function () {
alert('load event'); // never fired
});
Example here.
Augmenting the Object.prototype
object in that way is never recommended, because those properties will be inherited by a great number of objects -even also by some host objects-, and as you know, the primary concern is that they will be enumerated by the for-in
statement.
In ECMAScript 5, now a safer way exist, because we can now declare non-enumerable properties, for example:
Object.defineProperty(Object.prototype, 'foo', { value: 'bar' });
In the property descriptor -{ value: 'bar' }
- we can specify property attributes, in the case of Value Properties as in the above example, we can specify the writable
attribute, and the common configurable
attribute (determines if a property can be re-configured -attribute changes- or deleted.
And we have also the enumerable
attribute, which determines if the property will be enumerated by the for-in
statement.
If we don't specify the attributes, they are false
by default, the descriptor will look like:
{
value: 'bar',
writable: false,
configurable: false,
enumerable: false
}
精彩评论