2015-06-30 70 views
1

所以我試圖掌握JavaScript並練習我正在嘗試做一個反應時間測試。這個想法很簡單:你點擊一個按鈕,經過一段隨機的時間後,背景顏色會變化,然後你必須點擊第二個按鈕,這個按鈕會調用一個函數來計算你的反應時間。這裏是我的JavaScript代碼:javascript函數未定義,但我的腳本正在加載

function start(){ 
    console.log(start); 
    var rndnr = (Math.round(Math.floor(Math.random() * 5) + 1)) * 1000); 
    setTimeout(function timeout() { 
     document.bgColor="ffff00"; 
     start = new Date(); 
    }, rndnr); 
} 

function stop() { 
    var onclick = new Date(); 
    var time = onclick-start; 
    var total; 
    var avg; 
    var count = 1; 
    document.getElementById("try 1").innerHTML = time; 
    total = total + time; 
    avg = total/count; 
    count = count + 1; 
    document.getElementById("avg1").innerHTML = avg; 
} 

,這些都是我的按鈕:

<button id="button" onclick="start()" >start</button> 
<button onclick="stop()">stop</button> 

當我嘗試在我的控制檯日誌它說這個執行腳本我得到一個錯誤:ReferenceError: start is not defined。我哪裏錯了?

+0

這似乎是功能全球範圍內都沒有申報? –

+0

什麼是確切的錯誤信息?它是:「ReferenceError:啓動未定義」或「ReferenceError:啓動不是函數」? –

+0

您可能試圖在聲明它之前調用該函數。 –

回答

2

您的代碼不少錯別字,以及一些命名衝突和範圍的問題。這是你的原代碼(除了在瀏覽器中重命名stopstopF因爲stop is a global function

function start() { 
 
    console.log(start); 
 
    // THE REFERENCE ERROR STEMS FROM THIS LINE PREVENTING THE FUNCTIONS 
 
    // FROM BEING DEFINED 
 
    var rndnr = (Math.round(Math.floor(Math.random() * 5) + 1)) * 1000); 
 
    setTimeout(function timeout() { 
 
    document.bgColor = "ffff00"; 
 
    start = new Date(); 
 
    }, rndnr); 
 
} 
 

 
function stopF() { 
 
    var onclick = new Date(); 
 
    var time = onclick - start; 
 
    var total; 
 
    var avg; 
 
    var count = 1; 
 
    document.getElementById("try 1").innerHTML = time; 
 
    total = total + time; 
 
    avg = total/count; 
 
    count = count + 1; 
 
    document.getElementById("avg1").innerHTML = avg; 
 
}
<button id="button" onclick="start()">start</button> 
 
<button onclick="stopF()">stop</button> 
 
<div id="try 1"></div> 
 
<div id="avg1"></div>

如果單擊「運行的代碼片斷」,你會發現在控制檯的錯誤:

Uncaught SyntaxError: Unexpected token) 

由於這個錯誤,既沒有定義start也沒有定義stopF因此,當點擊開始按鈕時,i nline JS將被評估,然後嘗試找到不存在的start函數,從而產生ReferenceError。同樣,如果點擊停止按鈕,它也將記錄ReferenceErrorstopF

糾正一些在代碼中的問題給出:

// You need to have a way of referencing the `start` variable (now `startTime`) 
 
// between the `start` and `stop` functions. 
 
// You also need to be able to keep state for `total` and `count` between 
 
// subsequent calls to `stop` 
 
// These issues can be solved by using scope variables 
 
// (here they are in the IIFE scope of the wrapper function) 
 
var startTime; 
 
var total = 0; 
 
var count = 0; 
 

 
// You had a name collision here within the scope of `start` 
 
// you also had attempted to use a variable named `start` 
 
// Now the variable is called `startTime` 
 
function start() { 
 
    // You had an extra ')' in your expression assignment for `rndnr` 
 
    var rndnr = (Math.round(Math.floor(Math.random() * 5) + 1) * 1000); 
 
    setTimeout(function timeout() { 
 
    document.bgColor = "ffff00"; 
 
    startTime = new Date(); 
 
    // Since setTimeout is an async function console.log would be undefined 
 
    // until this function runs 
 
    console.log(startTime); 
 
    }, rndnr); 
 
} 
 

 
function stop() { 
 
    var onclick = new Date(); 
 
    var time = onclick - startTime; 
 
    var avg; 
 
    total += time; 
 
    avg = total/++count; 
 

 
    // You shouldn't include spaces in ID values as it can be confusing 
 
    // if this was intentional 
 
    document.getElementById("try1").innerHTML = time; 
 
    document.getElementById("avg1").innerHTML = avg; 
 
    document.bgColor = "ffffff"; 
 
}
<button id="button" onclick="start()">start</button> 
 
<button onclick="stop()">stop</button> 
 
<div id="try1"></div> 
 
<div id="avg1"></div>

1

編輯:

這裏是你的代碼的工作版本(僅停止按鈕需要標籤「嘗試1」和「平均」)

http://jsfiddle.net/2q84yvzu/

問題是在額外)上:

var rndnr = (Math.round(Math.floor(Math.random()*5)+1))*1000); 

這是正確的版本:

var rndnr = (Math.round(Math.floor(Math.random()*5)+1))*1000; 

我改變了將事件綁定到元素的方式,嵌入事件並不是一種好的做法。相反,嘗試下一個方法:

document.getElementById('start').onclick=function(){start();}; 
document.getElementById('stop').onclick=function(){stop();}; 

有關此更多的信息,這裏是另外一個問題:

Inline onclick JavaScript variable

+0

雖然這是正確的,可能不是OP的意圖,但這與上述錯誤有什麼關係? –

+0

嘗試在函數內部記錄函數引用。它不會在您的控制檯中出錯。 –

-2
console.log(start); 

是錯誤的

它必須是

console.log("start"); 

,或者你必須創建變量開始

var start = "put anything in here"; 
console.log(start); 
+1

start是函數的定義名稱。它存在 –

+0

他爲什麼要打印該功能? – Kbi

+1

不要緊,爲什麼,這不是錯誤 –

1
var rndnr = (Math.round(Math.floor(Math.random()*5)+1))*1000); 

語法錯誤,應該是

var rndnr = (Math.round(Math.floor(Math.random()*5)+1))*1000; 
2

爲了確保文檔知道的start功能,這樣做:

window.start = function start(){ ... }; 

或者確保在分配處理程序之前加載腳本。

其次,不要嘗試設置一個值來啓動,因爲start指的是一個函數。改用startTime或其他變量。

startTime = new Date(); 
+0

雖然這些都是很好的建議,他們不回答OP的問題。有關ReferenceError的原因,請參閱[我的答案](http://stackoverflow.com/a/31141237/3194372)。 –

+0

@JasonCust他們實際上回答了這個問題。 '未捕獲的ReferenceError:啓動未定義'http://jsfiddle.net/sj4yz3a6/ http://jsfiddle.net/sj4yz3a6/1/該OP沒有要求他的代碼被修復,但是是什麼導致了問題。 –

+0

'ReferenceError'出現是由於JS引擎由於額外的')'而無法解析函數的代碼。雖然你提到的值得注意,但函數從未被聲明,因爲'Uncaught SyntaxError:Unexpected token')錯誤。我還修復了代碼,指出修復該錯誤之後會影響它的其他問題。 –

0

您需要重命名變量start setTimeout函數裏面,因爲你start()函數的第一個電話後重寫功能開始與日期值。

function f(){ 
 
    setTimeout(function(){ f = 1; }, 1000); 
 
} 
 

 
console.log(f); // function 
 

 
f(); 
 

 
setTimeout(function(){ 
 
    console.log(f); // 1 
 
}, 1100);

相關問題