在给定时间内正确回答

Correct answer within a given time

提问人:Tessa 提问时间:8/24/2021 最后编辑:SpankiedTessa 更新时间:8/25/2021 访问量:112

问:

我正在尝试在 Gorilla experiment builder 中创建一个使用特定 js Gorilla 钩子的实验。

参与者可以被重定向到3种类型的屏幕:“正确和快速”屏幕(如果他们回答不到2秒),“正确但缓慢”屏幕(如果他们回答超过两秒)和“不正确”屏幕(如果他们给出错误的回答)。

这是我拥有的代码。第一个 while 循环有效,但一旦它试图将参与者重定向到“正确的快速”屏幕以外的内容,它就会失败。

我根本不是 javascript 专家,所以这可能只是我写它的方式,但我似乎无法弄清楚。

//If the RT is FAST (less than 2 seconds AND correct, move to a correct fast screen)
var reactionTime = gorilla.readStopwatch();    
while (reactionTime <= 2000) {
    if (response == "g") {
        //If the RT is slow but still correct, move to a correct slow screen.     
        return { new_screenName: 'Correct_fast'};
    }  
    while (reactionTime > 2000) {
        if (response == "g") {
            //If the response is incorrect, move to an incorrect screen.  
            return { new_screenName: 'Correct_slow'};
        } else if (response == "h") {
            return { new_screenName: 'Incorrect'};
        }
    } 
}
javascript if-statement while-loop 大猩猩

评论


答:

0赞 Spankied 8/24/2021 #1

我对大猩猩一无所知,但这里有一个香草 js 计时器。

let start, slow = false;

function step(timestamp) {
  start ??= timestamp;
  const elapsed = timestamp - start;

  if (elapsed > 2000) slow = true; // slow = true after 2 seconds

  if (elapsed < 2000) { // Recursion loop ends after 2 seconds
    window.requestAnimationFrame(step); 
  }
}

window.requestAnimationFrame(step); // requestAnimationFrame passes step() one argument, a DOMHighResTimeStamp similar to the one returned by performance.now()

处理异步事件之间的时间可能需要高级 JS 技能/经验,并且是被迫快速学习很多东西的好方法。以下是我解决这个问题的方法。

async function TestExperiment(){
    var answer, wasSlow, newScreenName; 

    [answer, wasSlow] = await Promise.all([getAnswer(), checkIfSlow()])
    
    if (answer == 'wrong') newScreenName = 'incorrect' 
    else if (!wasSlow) newScreenName = 'correct_fast'
    else if (wasSlow) newScreenName = 'correct_slow'
        
    console.log('New Page =>', newScreenName)

    function checkIfSlow(){
        return new Promise( resolve => {
            let start, slow = false;
            function step(timestamp) {
                start ??= timestamp;
                const elapsed = timestamp - start;
                if (answer) resolve(slow) // resolve early if answer set before 2 seconds
                if (elapsed > 2000) { // resolve after 2 seconds
                    slow = true;
                    resolve(slow)
                }
                if (elapsed < 2000) {
                    window.requestAnimationFrame(step);
                }
            }
            window.requestAnimationFrame(step);
        })
    }
    function getAnswer() {
        return new Promise( resolve => { 
            let correctBtn = document.getElementById('correct')
            let wrongBtn = document.getElementById('wrong')
    
            correctBtn.onclick = () => {
                answer = 'correct'
                resolve(answer)
            }
            wrongBtn.onclick = () => {
                answer = 'wrong'
                resolve(answer)
            }
         });
    }
}

TestExperiment()
<button id="correct">correct</button>
<button id="wrong">wrong</button>

0赞 Friedrich 8/24/2021 #2

我认为您的问题可能是,您的第二个 while 循环嵌套到您的第一个 while 循环中,所以现在您的代码仅在 reactionTime 小于 2000 时才检查 reactionTime 是否大于 2000。您可以进行 2 个循环,也可以只验证何时给出响应

if(response == 'g' && reactionTime <= 2000){
    return { new_screenName: 'Correct_fast'};
else if(response == 'g'){
    return { new_screenName: 'Correct_slow'};
}else{
    return {new_screenName: 'Incorrect'};
}