Javascript 使用此内部对象数组

Javascript 使用此内部对象数组,javascript,arrays,javascript-objects,Javascript,Arrays,Javascript Objects,我有一个用构造函数创建的对象数组。这是构造函数的定义: function Expander(elem, startingFlipped) { this.element = elem; this.flipped = startingFlipped; } (下面,rawlems只是document.getElementsByClassName('foo');) 触发DOMContentLoaded事件后,我将执行以下操作以查找、构造新对象并将其推入数组: for (var i = 0; i

我有一个用构造函数创建的对象数组。这是构造函数的定义:

function Expander(elem, startingFlipped) {
  this.element = elem;
  this.flipped = startingFlipped;
}
(下面,
rawlems
只是
document.getElementsByClassName('foo');

触发DOMContentLoaded事件后,我将执行以下操作以查找、构造新对象并将其推入数组:

for (var i = 0; i < rawElems.length; i++) {
  expanders[i] = new Expander(rawElems[i], false);

  expanders[i].this.element.addEventListener("click", function (event) {
    console.log("Clicked " + expanders[i].this.element);
  });
}
for(变量i=0;i
问题是,我不知道访问
this
属性的语法如何。这将当前引发错误:

未捕获的TypeError:无法读取未定义的属性“element” 在HTMLSPANENT

这在某些方面是很好的,因为它们是
元素(控制台记录对象和数组显示它已正确填充)


但是,既然我正在尝试这种构造函数模式,那么如何使用
this
正确引用每个对象中的元素呢?

表达式
expanders[I]。this.element
的意思是“在
扩展器
上查找属性,其名称为
i
的值,然后在结果上查找名为
this
的属性,并在结果上查找名为
element
的属性。”

但是您的
扩展器
对象上没有名为
this
的属性。如果要访问位于
expanders[i]
Expander
对象,只需使用它,而不需要将
此添加到它中。

expanders[i].element.addEventListener("click", function (event) {
//          ^--- No this. here
    console.log("Clicked " + this);
    // Here, use `this` -----^
});
在事件处理程序中,
将引用挂接事件的DOM元素,因此根本不通过
扩展器
访问它

如果需要访问其中的扩展器,则需要为自己提供一个引用,该引用在事件发生时仍然有效。您不能在当前循环中使用
扩展器[i]
,因为
i
的值在事件发生之前已经更改

此部分有很多选项,在中讨论。最简单的方法之一是使用
Array.prototype.forEach
而不是
for

Array.prototype.forEach.call(rawElems, function(element, index) {
    var expander = expanders[index] = new Expander(element, false);
    element.addEventListener("click", function (event) {
        // You can use `element` and `expander` here
        // If you liked, you could *not* have the `expander` variable
        // and use `expanders[index]` here, because unlike the `i` in
        // your `for` loop, the value `index` won't change.
    });
});
在ES2015(也称为“ES6”)或更高版本的环境中,您可以在
for
循环中使用
let
for(let i=0;i
然后
扩展器[i]
将正常工作。(
let
var
大不相同,尽管它们有相似的用途。)

或者您可以使用
Function.prototype.bind
扩展器[i]
绑定到事件处理程序函数,然后使用
this
引用扩展器,使用
this.element
(或
event.currentTarget
)引用元素。这样做的好处是,您可以一次性定义处理程序并重用它:

for (var i = 0; i < rawElems.length; i++) {
  expanders[i] = new Expander(rawElems[i], false);
  expanders[i].element.addaddEventListener("click", handleExpanderClick.bind(expanders[i]));
}
function handleExpanderClick(event) {
    // `this` = the expander
    // `this.element` = the element
    // `event.currentTarget` = the element (also)
}
for(变量i=0;i
试试
扩展器[i].element…
@PranavCBalan我还是会遇到同样的错误,事实上(我也试过)哦!有趣。我还可以简单地使用
.map()
方法将事件处理程序分配给数组中的每个object.element吗?@armadadrive:Doh!当然您可以:
var expanders=Array.prototype.map.call(rawlems,function(element,index){/*create,hook-up,并在这里返回expander*/})