delete
运算符从对象中删除属性。如果我在window
上设置了一个属性,我可以将其删除:
window.myProp = 10;
delete window.myProp;
作为the article我经常在涉及delete
运算符状态的行为时引用其他人,这是因为属性赋值不设置DontDelete
属性(而不是{变量声明,确实如此)。
该文章还指出了以下内容(重点补充):
请注意,在属性创建期间,属性是 确定(即没有设定)。 以后的作业不会修改 现有财产的属性。理解这一点很重要 区别。
请注意,为什么我可以覆盖窗口的现有属性alert
,然后将其删除为返回原始值?我错过了一些明显的东西吗我很少使用delete
运算符,所以很可能就是这种情况。
例如:
window.alert = function() {};
alert("Hi!"); //Nothing happens
delete window.alert;
alert("Hello?"); //Alerts 'Hello?'
这里有一个fiddle来证明这一点(仅在Chome进行过测试,非常确定IE不会以这种方式运行,但现在除了Chrome之外无法访问任何内容)。
答案 0 :(得分:9)
在Chrome中,window.alert
函数是DOMWindow
类的原型的一部分,它不是window
本身的属性。
因此,当您覆盖window.alert
时,您正在向window
添加 new 属性,但原型中的版本仍然存在,但是已隐藏。
当delete window.alert
重新暴露原型中的函数时。
这是一些控制台输出,显示该函数在原型中:
> window.constructor.prototype
DOMWindow
> window.constructor.prototype.alert
function alert() { [native code] }
Firefox的行为类似,尽管有不同的类名。
答案 1 :(得分:2)
这是预期的行为,称为阴影。它允许您提供自定义功能,而不会消除超类的功能。删除方法时,将删除自定义方法,从原型中显示原始方法。
你越接受继承并理解原型的工作方式,你就越会发现自己看到人们这样做的实例。
很好的问题。根据我的经验,这不是大多数JavaScript开发人员经常探索的领域。如果不是这种类型的东西,那么扩展或覆盖JavaScript基础对象的核心功能的许多polyfill是不可能的。