gpt4 book ai didi

javascript - 防止新的原型(prototype)方法出现在对象中的键的 for 循环中

转载 作者:行者123 更新时间:2023-11-30 00:28:47 24 4
gpt4 key购买 nike

我有一个函数,我想让它对所有对象可用。它的 mergeObject(object) 函数定义如下:

Object.prototype.mergeObjects = function(object){
if (typeof object != "object") return;
for(var key in object){
if (object.hasOwnProperty(key))
this[key] = object[key];
}
return this;
}

我有一个变量事件是:

events : {
"click #retryBtn":"onRetryBtnClick",
"click #cancelBtn":"onCancelBtnClick",
"click .dialogButton":"onDialogBtnClick"
}

这是 Backbone 的事件 json 对象。

当我尝试为事件中的键运行 for 循环时

for (var key in events) 
{
console.log(key)
}

打印出来

click #retryBtn
click #cancelBtn
click .dialogButton
mergeObjects

我不明白为什么我将“mergeObjects”作为“事件”对象中的键。

事件对象的结构是:

click #cancelBtn: "onCancelBtnClick"
click #retryBtn: "onRetryBtnClick"
click .dialogButton: "onDialogBtnClick"
__proto__: Object
__defineGetter__: function __defineGetter__() { [native code] }
__defineSetter__: function __defineSetter__() { [native code] }
__lookupGetter__: function __lookupGetter__() { [native code] }
__lookupSetter__: function __lookupSetter__() { [native code] }
constructor: function Object() { [native code] }
hasOwnProperty: function hasOwnProperty() { [native code] }
isPrototypeOf: function isPrototypeOf() { [native code] }
mergeObjects: function (object){
propertyIsEnumerable: function propertyIsEnumerable() { [native code] }
toLocaleString: function toLocaleString() { [native code] }
toString: function toString() { [native code] }
valueOf: function valueOf() { [native code] }
get __proto__: function __proto__() { [native code] }
set __proto__: function __proto__() { [native code] }

谁能解释为什么“mergeObject”是 for 循环键的一部分?

如何避免?因为还有其他方法,如“__defineGetter”,它没有出现在 for 循环键中。

最佳答案

mergeObjects 是可枚举属性(意味着它可以使用 for in 访问),它被 events 对象继承,而像 __defineGetter 这样的方法是不可枚举(不能被for in访问)。

for in循环遍历对象的所有可枚举属性,包括原型(prototype)链中的属性。

使用hasOwnProperty避免继承属性,只获取直接可枚举属性。

for (var key in events) 
{
if(events.hasOwnProperty(key))
console.log(key)
}

如果你想要一个对象的所有直接属性都是可枚举的或不可枚举的(使用 defineProperty 和可枚举的 false 设置)那么你应该迭代 Object.getOwnPropertyNames() (IE9+) 喜欢

var keys = events.getOwnPropertyNames(); 
for(var i=0;i<keys.length;i++)
{
console.log(keys[i])
}
/*
Or using forEach
events.getOwnPropertyNames().forEach(function(key){
console.log(key);
})
*/

附加链接 https://developer.mozilla.org/en-US/docs/Web/JavaScript/Enumerability_and_ownership_of_properties

编辑:为了不让 mergeObjects 进入 for in 循环,请使用 Object.defineProperty 和可枚举的 false,例如

Object.defineProperty(Object.prototype, 'mergeObjects', {
value: function(object){
if (typeof object != "object") return;
for(var key in object){
if (object.hasOwnProperty(key))
this[key] = object[key];
}
return this;
},
enumerable:false //no need for this statement as default is false
});

IE9及以上版本有效

关于javascript - 防止新的原型(prototype)方法出现在对象中的键的 for 循环中,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30391814/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com