假设我们在for循环中有一个简单的print语句,例如
for (var i = 0; i < 2; i++){
setTimeout(() => console.log(i));
}
两个问题。
setTimeout是一种浏览器API方法,但是它如何访问i
? i
在for循环中声明,即使没有通过i
,我也在方法setTimeout
中访问i
,怎么办?
为什么要打印2,2,而不是0.1?
答案 0 :(得分:2)
setTimeout是一种浏览器API方法,但是它如何访问i?我是 在for循环内声明,并且我正在方法内访问i setTimeout即使我没有通过,怎么办?
在javascript中,嵌套函数可以访问高阶变量和函数。
//global context - any variable declared here will be availabe within any nested function
var someVariable = 0;
var someSecondVariable = 1;
const someFunc = () => {
//someVariable and someSecondVariable are accessible here
console.log("someFunc", someVariable, someSecondVariable);
var someThirdVariable = 2;
for(let i = 0; i < 5; i++){
const temp = i;
//all higher order variables are still accessible
setTimeout(()=>{
//all higher order variableds are still accessible
console.log("settimeout", i, temp);
}, 4000);
}
}
const someFunc2 = () => {
//cant access someThirdVariable
try {
console.log("someFunc2", someThirdVariable);
}catch(e){
console.warn(e.message);
}
}
someFunc();
someFunc2();
为什么要打印2,2而不是0,1?
setTimeout是一种异步方法,不会立即被调用。在第一个超时事件开始之前,循环结束。这意味着,在调用setTimeout回调时,我已经等于2。
然后调用setTimeout回调
console.log(i) //where i = 2
console.log(i) //where i = 2
在这里您可以拥有0,1
for (var i = 0; i < 2; i++){
//temp won't get increased in the next iteration
const temp = i;
setTimeout(() => console.log(temp));
}
例如,与php相比,它有所不同,我们必须明确告诉它使用更高阶的变量,以便能够在函数范围内访问它。
<?php
$i = 0;
$func = function() use ($i){
echo $i;
};
$func();