for (var i=0, link; i<5; i++) {
link = document.createElement("a");
link.innerHTML = "Link " + i;
link.onclick = function (num) {
return function () {
alert(num);
};
}(i);
document.body.appendChild(link);
}
由于嵌套函数是一个闭包,它有一个对num
参数的引用,循环结束时的num
参数是4.当第一个元素被点击时,为什么它会发出警报1?它应该警告4。警报1的原因是什么?不引用num
参数?或者是什么原因?
但这里的情况有所不同:
function foo(x) {
var tmp = 3;
return function (y) {
alert(x + y + (++tmp));
}
}
var bar = foo(2); // bar is now a closure.
bar(10);
上面的函数会提醒16,因为bar仍然可以引用arg x
和tmp
,即使它不再直接在范围内。
这证明了闭包还引用了参数值,而不是为什么上面的代码每次都没有提醒4?
答案 0 :(得分:3)
for (var i=0, link; i<5; i++) { //i starts at 0 and iterates up to 4
link = document.createElement("a");
link.innerHTML = "Link " + i;
link.onclick = function (num) {
//num is never changed within this function, and is equal
//to the value of i when it was passed in
return function () { alert(num);};
}(i); //i is passed here
//that sets num to the current value of i for each link
document.body.appendChild(link);
}
对于第一个链接,num将为0,因为i
在传递给外部函数时为1。然后,我会循环每次循环,并且每个链接的值都不同。
这里的模式是一种非常常见的模式,用于保留回调/事件绑定中循环迭代的当前值。
答案 1 :(得分:0)
你正在做的是避免的经典例子,点击第一个元素会给你4而不是1,这应该是最期望的值。
如果您希望它提醒1,那么就这样做:
link.onclick = function() {alert(i);};
但老实说,这有什么意义呢?所有4个链接都会提醒4 ...