Attempt to delete prototype of HTMLElement fails
I was trying to delete .insertBefore();
of HTMLElement.prototype
but when I check for it, instead of an undefined value, it returns the actual function? Why?
console.log(HTMLElement.prototype.insertBefore); // function insertBefore() { [native code] }
delete HTMLElement.prototype.insertBefore;
console开发者_JAVA百科.log(HTMLElement.prototype.insertBefore); // function insertBefore() { [native code] }
Can you explain why this isn't working. I tried this on my own constructor and it worked, but for the built in ones, it didn't.
You cannot use DELETE like that:
http://perfectionkills.com/understanding-delete/
Property attributes
Every property can have zero or more attributes from the following set — ReadOnly, DontEnum, DontDelete and Internal. You can think of them as flags — an attribute can either exist on a property or not. For the purposes of today’s discussion, we are only interested in DontDelete.
Built-ins and DontDelete
So this is what it’s all about: a special attribute on a property that controls whether this property can be deleted or not. Note that some of the properties of built-in objects are specified to have DontDelete, and so can not be deleted. Special arguments variable (or, as we know now, a property of Activation object) has DontDelete. length property of any function instance has DontDelete as well.
Seriously man, read that article. It has a ludicrously clear and concise explanation of all this!
Note: even though they have the dontDelete
attribute set, you can still overwrite it:
HTMLElement.prototype.insertBefore = '';
// or
HTMLElement.prototype.insertBefore = null;
// or
HTMLElement.prototype.insertBefore = undefined;
The browser implementation(s) probably have that property set as non-configurable.
There may be a greater chance that it is writable though:
HTMLElement.prototype.insertBefore = null;
console.log(HTMLElement.prototype.insertBefore); // null
Keep in mind that objects like HTMLElement
are host objects, and therefore don't necessarily follow all the same rules of regular JavaScript objects.
For example, trying to delete
a non-configurable property when in strict mode should throw an error, but testing this in Chrome, no error is thrown.
http://jsfiddle.net/YrvE4/2/
Seen here, you if you create your own custom property, you can delete
that just fine:
"use strict";
HTMLElement.prototype.custom_property = 'value'; // new property
console.log(HTMLElement.prototype.custom_property); // value
try {
delete HTMLElement.prototype.custom_property;
} catch (e) {
console.log(e);
}
console.log(HTMLElement.prototype.custom_property); // undefined
http://jsfiddle.net/YrvE4/3/
HTMLElement.prototype
, like all of DOM, is a "host object", which is basically something provided by the ECMAScript environment that isn't defined in the ECMAScript spec. Host objects have few rules they have to follow: it is perfectly allowable for [[Delete]]
to do nothing, even if Object.getPropertyDescriptor
has [[Configurable]]: false
.
精彩评论