我有一个 html 文件,上面有一个按钮
<!DOCTYPE html>
<html> <body>
<p>Click the button to list all the items in the array.</p>
<button onclick = "numbers.forEach(myFunction)" >Try it</button>
<p id="demo"></p>
</body>
</html>
我还有包含 .forEach
方法的 onclick
函数的 Javascript 文件。
单击按钮时,我想遍历一个数组,循环遍历数组中的每个元素实例。
对于这个数组中的每个元素,我想用一个计时器打印出它的索引和值,然后等待一秒钟以显示下一个排列。
demoP = document.getElementById("demo");
var numbers = [];
var random = Math.floor(Math.random() * 4) + 1;
numbers.push(random);
function myFunction(item, index) {
random = Math.floor(Math.random() * 4) + 1;
numbers.push(random);
demoP.innerHTML = demoP.innerHTML + "numbers[" + index + "]: " + item + "<br>";
//demoP.innerHTML = demoP.innerHTML + "<br>" //add magic spacing between permutation
sleep(100);
//switch to this and see how slow?
//sleep(1000);
}
function sleep(milliseconds) {
var start = new Date().getTime();
for (var i = 0; i < 1e7; i++) {
if ((new Date().getTime() - start) > milliseconds){
break;
}
}
}
我希望用户点击按钮时显示的结果是:
numbers[0] = 4
//waits a second and adds a <br> here to separate
numbers[0] = 4
numbers[1] = 2
//waits a second and adds a <br> here
numbers[0] = 4
numbers[1] = 2
numbers[2] = 3
等等。
目前,代码输出的元素数量至少是原来的两倍,而且 sleep() 的持续时间似乎比应有的要长。
最佳答案
除了可怕的 sleep
函数。您正在使用 myFunction
作为 forEach
的回调,并且在 myFunction
中,您正在将新元素推送到 numbers
与您调用 forEach
的数组相同。
forEach
不会在仍然循环数组的同时对新推送的项目调用回调。但是到循环结束时,数组中的项目将加倍。根据 MDN:
The range of elements processed by
forEach()
is set before the first invocation ofcallback
. Elements that are appended to the array after the call toforEach()
begins will not be visited bycallback
.
如果数组包含N
个元素,那么当点击发生时,N
个元素将被显示,myFunction
将推送 N
个其他元素,当下次点击发生时,这次将显示 2N
个元素,...
所以每次点击之后,数组中的元素都会翻倍。
关于Javascript array.forEach(function) 执行函数的次数是预期的两倍,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47723375/