为什么我不能将函数调用(而不是函数引用或匿名函数)传递给setTimeout()?
问题描述:
请忽略这样的事实,即这段代码什么都不做,并且对可能是一个疯狂的问题表示歉意!为什么我不能将函数调用(而不是函数引用或匿名函数)传递给setTimeout()?
据我所知,我不能通过函数调用setTimeout()
作为第一个参数,但为什么我不能这样做?
let names = ['Andy', 'Ross', 'David'];
function printer (name) {
console.log(name);
}
names.forEach(name => setTimeout(printer(name), 1000);
结果:
Andy
timers.js:327
throw new TypeError('"callback" argument must be a function');
^
我可以解决,而不是使用参考printer
使用bind()
送与它一起name
的问题,但我为什么一定要把这些额外的步骤?
let names = ['Andy', 'Ross', 'David'];
function printer (name) {
console.log(name);
}
names.forEach(name => setTimeout(printer.bind(null, name), 1000));
结果:
Andy
Ross
David
答
你可以试试这个:
setTimeout(function(){printer(name)}, 1000)
答
setTimeout
应该采取一个函数作为第一个参数。
请参考:
https://www.w3schools.com/jsref/met_win_settimeout.asp
这里要传递的功能是undefined
第一个参数的结果。
答
你可以这样说:
setTimeout(printer, 1000, name)
答
传递函数引用的正确方法是使用回调。
names.forEach(name => setTimeout(function() {
printer(name);
}, 1000));
回调包含对函数的引用。
setTimeout(callbackFunction, milliseconds);
答
这是因为执行的顺序。如果您将函数调用传递给setTimeout,则该函数将立即执行,即该函数立即放入JavaScript的执行堆栈中。
如果您传递函数名称,即对函数的引用,则只有在定时器完成后才会将函数放入JavaScript线程的执行堆栈中。
+0
谢谢,这很有道理!我很感激 – NoobOfNoobs
因为setTimeout应该会收到一个应该稍后调用的回调 –