函数的调用时机是函数的要素之一。调用时机不同,输出的结果就会不同。
首先简单地定义并调用一个函数:
function fn(){
console.log('fn被调用了')
}
fn()
console.log('调用完fn后打印了这句话')
输出结果为
解释为什么如下代码会打印 6 个 6
let i = 0
for(i = 0; i<6; i++){
setTimeout(()=>{
console.log(i)
},0)
}
setTimeout()是指设置一个定时器,该定时器在定时到期后执行一个函数或指定的一段代码。
setTimeout()是异步函数,同时JS又是单线程运行,所以会等全局进程的代码执行完毕之后,再执行消息队列的任务。在这个例子里,在for循环执行完成后,此时i的值是跳出循环是i的值,为6,此时开始执行setTimeout函数,打印6次i的值,所以结果为6个6.
若想让for循环中的setTimeout输出0 1 2 3 4 5
可以用
for(let i = 0; i<6; i++){
setTimeout(()=>{
console.log(i)
},0)
}
在for循环中初始化语句,在循环开始之前初始化变量,而且let是块级作用域,每次执行都是一个全新的独立的块作用域,使用let声明的变量作为迭代器变量传入到 for循环体的作用域后,不会发生改变,不受外界的影响。
可是又因为 let是块级作用域,可每次执行的循环都是一块独立的块作用域,那么下一个的循环是接收不到上一块的let定义的变量的,那么整个循环就没办法一次次的进行下去。
所以for循环里的迭代器变量i 就是每次循环都会进行一次的声明赋值。保留在那次执行循环的一块独立的块作用域内。
除了for循环里用let初始化变量之外,可以使用立即执行函数
let i = 0
for(i = 0; i<6; i++){
!function(i){
setTimeout(()=>{
console.log(i)
},0)
}(i)
}
还可以使用setTimeout的第三个参数
let i = 0
for(i = 0; i<6; i++){
setTimeout((i)=>{
console.log(i)
},0,i)
}
使用const关键字
let i
for(i = 0; i<6; i++){
const x = i
setTimeout(()=>{
console.log(x)
})
}