当我点击按钮时,我有两个应该运行的功能。第一个函数是一个setInterval函数,它将变量 num 递增0.01并将其显示在名为 result 的div id中。第二个函数将对象文字生成为json字符串,并将其显示在名为 output 的div id中。当我单击按钮时,只输出JSON字符串,但似乎setInterval没有运行,我不知道为什么。以下是link例如
HTML
<button>
click
</button>
<div id="result">
</div>
<div id="output">
</div>
的Javascript
var timer,
result = document.getElementById("result"),
num,
link ={
name:"link",
weapon:"master sword",
mute:true,
race:"hyrulian",
age:16
};
/* ---------- GENERATE JSON OBJECT --*/
function generate(){
var data = {};
for(var prop in link){
data[prop] = link[prop];
}
data = JSON.stringify(data);
document.getElementById("output").innerHTML = data;
}
/* ---------- CLICK BUTTON --*/
document.querySelector("button").onclick = function(){
num = 0;
function callBack(){
num += 0.01;
result.innerHTML = num.toFixed(2);
}
timer = setInterval(callBack,10);
generate();
clearInterval(timer);
}
答案 0 :(得分:1)
更新了我的答案:你必须包装你的callBack();使用匿名函数在setInterval
中运行。这是因为setInterval
期望对应该每隔几毫秒(您指定的间隔)执行的Function的引用。您应该像setInterval( function(){ callBack(); }, 10);
一样使用它。这应该会给你想要的结果。
相同的代码,我刚刚更新了setInterval( function(){ callBack(); }, 10);
行:
var timer,
result = document.getElementById("result"),
num,
link ={
name:"link",
weapon:"master sword",
mute:true,
race:"hyrulian",
age:16
};
/* ---------- GENERATE JSON OBJECT --*/
function generate(){
var data = {};
for(var prop in link){
data[prop] = link[prop];
}
data = JSON.stringify(data);
document.getElementById("output").innerHTML = data;
}
/* ---------- CLICK BUTTON --*/
document.querySelector("button").onclick = function(){
num = 0;
function callBack(){
num += 0.01;
result.innerHTML = num.toFixed(2);
}
timer = setInterval( function(){ callBack(); },10); // I modified this line
// timer = setInterval(callBack,10);
generate();
clearInterval(timer);
// setTimeout( function(){ clearInterval(timer); }, 1000); // This can be used to test that the timer has indeed started, you can wait 1 second before you clear the timer
}
答案 1 :(得分:0)
这是因为您setInterval(callBack,10);
,但是您使用clearInterval(timer);
清除了间隔。
删除clearInterval(timer);
,您就可以让计时器正常工作。
答案 2 :(得分:0)
JavaScript是单线程的。为了使您设置的callBack
函数在运行setInterval(callBack,10)
的10毫秒间隔内运行,您的JavaScript代码必须停止运行(即完成)。在您的代码放弃处理器之前,不会执行任何类型的回调函数。
因此,在您的代码中:
timer = setInterval(callBack,10); //Set up the interval timer
generate(); //generate(): Even if this takes 10 minutes to complete
// the callBack function will not be executed from the interval timer.
clearInterval(timer); //Clear the interval timer. While the interval may have expired
// (depending on how long the generate() function took), the
// the callBack function will have never run because the processor
// has been busy continuing to run the code that came after calling
// setInterval. Clearing the interval timer here results in
// callBack never being executed.
因此,如果您希望callBack
执行一次,则需要在您当时执行的代码完成之前不调用clearInterval(timer)
。
如果您希望callBack
只执行一次,那么您可以使用setTimeout()
。
如果您正在尝试计算某事需要多长时间:
window.performance.now()
“以毫秒为单位测量,精确到千分之一毫秒”。window.performance.now()
)。所以,修改你的代码:
var timer,
result = document.getElementById("result"),
link = {
name: "link",
weapon: "master sword",
mute: true,
race: "hyrulian",
age: 16
};
/* ---------- GENERATE JSON OBJECT --*/
function generate() {
var data = {};
for (var prop in link) {
data[prop] = link[prop];
}
data = JSON.stringify(data);
document.getElementById("output").innerHTML = data;
}
/* ---------- CLICK BUTTON --*/
document.querySelector("button").onclick = function() {
function showResult(time, precision, units) {
result.innerHTML = time.toFixed(precision) + ' ' + units;
}
var startTime = window.performance.now();
generate();
var endTime = window.performance.now();
//These times are floating point numbers in milliseconds
var elapsedMs = endTime - startTime;
showResult(elapsedMs,3,'milliseconds');
//If you want to show the time in microseconds:
//var elapsedUs = elapsedMs * 1000;
//showResult(elapsedUs,0,'microseconds');
}
<button>
click
</button>
<div id="result">
</div>
<div id="output">
</div>
但是,如果您的真正目标是确定运行generate()
所需的平均时间,那么您需要时间来运行生成大量的时间,而不仅仅是一次。
var result = document.getElementById("result");
var link = {
name: "link",
weapon: "master sword",
mute: true,
race: "hyrulian",
age: 16
};
/* ---------- GENERATE JSON OBJECT --*/
function generate() {
var data = {};
for (var prop in link) {
data[prop] = link[prop];
}
data = JSON.stringify(data);
document.getElementById("output").innerHTML = data;
}
/* ---------- CLICK BUTTON --*/
document.querySelector("button").onclick = function(event) {
//Should not do long things in an event handler.
//Thus, instead of actually performing the tests here, we set
// a timeout which will execute after the event has processed.
this.style.display = 'none'; //Only get to click once
setTimeout(performTimedTests,0,generate,result);
}
/*
* Perform multiple runs of an increasing number of iterations of a specified function.
*
* functionToTest = The function which is being timed
* resultsElement = An element in the DOM, usually a <div>, which will
* have its innerHTML replaced with a table of time results.
* start = The number of iterations to start with. (default = 1)
* end = The number of iterations to not exceed. (default = 1000000)
* multiplier = The amount multiply the current number of iterations to find
* the number of iterations for the next run. (default = 10)
*/
function performTimedTests(functionToTest,resultsElement,start,end,multiplier){
start=start?start:1;
end=end?end:1000000;
multiplier=multiplier?multiplier:10;
var textColors =['red','orange','yellow','green','blue','purple']
function timeAfunction(functionToTest, iterations){
var i, startTime, endTime;
startTime = window.performance.now();
for(i=0;i<iterations;i++){
functionToTest();
}
endTime = window.performance.now();
return (endTime - startTime);
}
function addResultToTable(table, elapsedTime, iterations, precision1, units1
, precision2, units2, scale2, name) {
var perCall = (elapsedTime/iterations)*scale2;
var newRow = table.insertRow(-1);
newRow.insertCell(-1).textContent = iterations;
newRow.insertCell(-1).textContent = elapsedTime.toFixed(precision1) + units1;
newRow.insertCell(-1).textContent = perCall.toFixed(precision2) + units2;
newRow.insertCell(-1).textContent = name;
}
function performNextTest(functionToTest,resultsElement,iterations,maxIterations
,multiplier,isFirstIteration){
var elapsedTime = timeAfunction(functionToTest, iterations);
var processing;
if(isFirstIteration) {
result.innerHTML = '<div></div>'
+'<table><tr><th>Iterations</th><th>Total time</th>'
+'<th>Time per<br/>Iteration</th>'
+'<th>Function<br>Tested</th></tr></table>';
processing = resultsElement.querySelector('div');
processing.textContent = 'Processing';
processing.style.color = textColors[0];
}
processing = resultsElement.querySelector('div');
var table = resultsElement.querySelector('table');
addResultToTable(table,elapsedTime,iterations,3,'ms',3,'us',1000
,functionToTest.name);
processing.textContent += '.';
//Cycle colors of 'Processing..' text
var colorIndex=textColors.indexOf(processing.style.color);
colorIndex++;
colorIndex = colorIndex>=textColors.length?0:colorIndex;
processing.style.color = textColors[colorIndex];
iterations *= multiplier;
if(iterations<=maxIterations) {
//Let the browser redraw
setTimeout(performNextTest,0,functionToTest,resultsElement,iterations
,maxIterations,multiplier,false);
}else{
processing.textContent = '';
processing.style.display = 'none';
}
}
performNextTest(functionToTest,resultsElement,start,end,multiplier,true);
}
<button>Start</button>
<div id="result"></div>
<div id="output"></div>