在while循环中使用setInterval的javascript不起作用

在while循环中使用setInterval的javascript不起作用,javascript,html,while-loop,Javascript,Html,While Loop,我正在开发一个迷你游戏,你必须点击正确的目标。我有一组不同id的div,编号从1到9。目标每3秒改变一次。为了选择目标,我做了一个函数,随机选择一个目标,直到用户点击正确的目标。这是我迄今为止编写的代码: let game; let victory = false; let target; const win = () => { victory = true; return alert('Has ganado'); } const setTarget = () =&

我正在开发一个迷你游戏,你必须点击正确的目标。我有一组不同id的div,编号从1到9。目标每3秒改变一次。为了选择目标,我做了一个函数,随机选择一个目标,直到用户点击正确的目标。这是我迄今为止编写的代码:

let game;
let victory = false;
let target;


const win = () => {
    victory = true;
    return alert('Has ganado');
}


const setTarget = () => {

    console.log("funcion setTarget");
    target = Math.floor(Math.random() * 9) + 1;

    // Añadimos la classe red
    document.getElementById(target).classList.add("target");

    // Al target actual le ponemos un eventlistener
    document.getElementById(target).addEventListener('click', win);

    return target;

}



// Al target anterior hay que eliminarle la classe red y quitarle el eventlistener
const removeTarget = () => {


    // Eliminamos la classe red
    document.getElementById(target).classList.remove("target");

    // Al target anterior le borro la classe "target"
    document.getElementById(target).removeEventListener('click', win);

    return target;

}


const startGame = () => {


    while (victory) {

        console.log("Entramos en el while");

        setTarget(); // Aplicamos estilo al target y le aplicamos event listener

        setTimeout(() => removeTarget, 30000); // Esperamos 3 segundos y eliminamos el target

    }

    return true;

}



// Ejecuta la función que hace todo el juego
startGame();
在函数startName中,我需要执行函数setTarget,然后等待3秒钟,然后执行removeTarget。这应该会发生,直到用户点击正确的元素。当用户单击正确的元素时,victory变为true,循环退出。现在,当我加载页面时,它根本不等待,而且速度非常快,以至于我看不到div正在改变颜色

这是可以使用的if的html:

<html>
    <head>
        <link rel="stylesheet" href="style.css">
    </head>
    <body>
        <div>
            <div id="1"></div>
            <div id="2"></div>
            <div id="3"></div>
          </div>
           
          <div>
            <div id="4"></div>
            <div id="5"></div>
            <div id="6"></div>
          </div>
           
          <div>
            <div id="7"></div>
            <div id="8"></div>
            <div id="9"></div>
          </div>


        <script src="script.js"></script>
    </body>
</html>
代码更改: 不要使用一段时间,这就是间隔的目的:

const startGame = () => {
    setTarget();
    window.my_interval = setInterval(adjustTarget, 30*1000);
}
然后,一旦用户获胜,清除间隔:

const win = () => {
    clearInterval(window.my_interval);
    removeTarget();
    alert('Has ganado');
}
您需要一个重置目标的临时方法。因此,请声明另一个为您执行此操作的函数,如:

function adjustTarget(){
    removeTarget();
    setTarget();
}
学习内容总结: 第一:胜利是假的,所以你的while循环永远不会进入。 第二:即使胜利是真的,您也会锁定运行时并获得超过最大调用堆栈大小的结果。while循环不等待setTimeout,因此它将设置数千/百万/数十亿个超时。 第三:不需要声明一个匿名函数,然后返回对removeTarget的引用。只需将removeTarget函数引用直接传递到setTimeout。 第四:当你调用StartName时,你的胜利起始值总是错误的。所以你不需要在游戏开始时检查它。 第五:考虑将所有代码放置在类中,以便更容易地进行变量、状态和范围管理。 第六:胜利甚至不需要变量,当用户单击“胜利”目标时,它就暗示了这一点。 第七:您没有使用任何方法的返回值。因此,您甚至不应该使用return语句。
看看这个,我已经更新了JavaScript中的几行代码,其余的保持不变

const win = () => {
victory = true;
clearInterval(startit);
return alert('Has ganado');
}

const startGame = () => {
    console.log("Entramos en el while");
    removeTarget(); // Esperamos 3 segundos y eliminamos el target
    setTarget(); // Aplicamos estilo al target y le aplicamos event listener
}

var startit = setInterval(startGame, 3000);
enter code here

while循环使javascript引擎保持忙碌,从不让循环外的任何代码停止执行,包括对setTimeout的回调。。。因此,胜利永远不会改变,但是,在您的情况下,while循环永远不会启动-因此其中的任何代码都不会运行。谢谢您的建议。已经进行了此更改,效果良好。我将再次研究您上面提到的所有这些概念,现在我发现我还没有完全理解:
const win = () => {
victory = true;
clearInterval(startit);
return alert('Has ganado');
}

const startGame = () => {
    console.log("Entramos en el while");
    removeTarget(); // Esperamos 3 segundos y eliminamos el target
    setTarget(); // Aplicamos estilo al target y le aplicamos event listener
}

var startit = setInterval(startGame, 3000);
enter code here