我有这个Javascript代码。
class MyLineEdit(QtGui.QLineEdit):
def focusInEvent(self, event):
print 'focus in event'
# do custom stuff
super(MyLineEdit, self).focusInEvent(event)
我这里有一个for循环,循环遍历一个充满函数的数组。在每次迭代中,检索数组中的函数并以时间间隔执行。
我想要的是在检索到最后一个函数之后,它从第一个函数开始再次循环遍历数组,并且将无限地执行此操作。
我尝试的是当计数器达到4时重置计数器但是它退出循环并继续执行,然后由于某种原因页面变得没有响应。
答案 0 :(得分:3)
您需要等到最后一次执行才设置下一次超时:
var headlineStore = [
function headline1(){
document.write('1');
},
function headline2(){
document.write('2');
},
function headline3(){
document.write('3');
},
function headline4(){
document.write('4');
},
function headline5(){
document.write('5');
}
]
function nextHeadline(index) {
headlineStore[index]();
window.setTimeout(
nextHeadline.bind(undefined, (index + 1) % headlineStore.length), 1000 );
}
nextHeadline(0);

答案 1 :(得分:1)
问题是这个函数会在第一个超时触发第一个数组函数之前永远循环。您需要在超时功能中增加循环。并让它等待。
试试这个:
var headlineStore = [
function headline1(){
//irrelevant code
},
function headline2(){
//irrelevant code
},
function headline3(){
//irrelevant code
},
function headline4(){
//irrelevant code
},
function headline5(){
//irrelevant code
}
]
var i = 0;
function loopForever(){
setTimeout(function(){
headlineStore[i]();
i++;
if(i == 5){
i = 0;
}
loopForever();
}, 5000 * (i + 1)); // I added the +1, else your first function fires immediately. seemed like you didn't want that.
}
答案 2 :(得分:1)
我认为这更符合您的需求(每5秒调用1次函数)。支持使用setTimeout取决于浏览器
var timeoutHandle = undefined;
headlineStore =
[ function1
, function2
, function3
...
];
function showHeadline(idx) {
headlineStore[idx](idx);
timeoutHandle = setTimeout(showHeadline, 5000, (idx+1)%headlineStore.length);
}
showHeadline(0);
答案 3 :(得分:0)
您可以使用.queue()
,.promise()
var headlineStore = [
function headline1(next) {
//irrelevant code
console.log("headline1");
setTimeout(next, 5000);
},
function headline2(next) {
//irrelevant code
console.log("headline2");
setTimeout(next, 5000);
},
function headline3(next) {
//irrelevant code
console.log("headline3");
setTimeout(next, 5000);
},
function headline4(next) {
//irrelevant code
console.log("headline4");
setTimeout(next, 5000);
},
function headline5(next) {
//irrelevant code
console.log("headline5");
setTimeout(next, 5000);
}
];
(function cycle() {
return $({}).queue("headlines", $.map(headlineStore, function(headline, i) {
return headline
})).dequeue("headlines")
.promise("headlines")
.then(cycle) // loop infinitely
}());

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js">
</script>
&#13;
答案 4 :(得分:0)
我不知道您要实现的目标,但我会尝试解释您的代码无效的原因。
JS在单线程上运行,您放在setTimeout
或setInterval
中的任何函数都在event queue
中排队。
此event queue
中的函数仅在运行JS代码的主要文件空闲时运行。
要解释我所说的内容,请遵循以下代码
(function() {
// A function queued to be called after 200 ms but it gets called
// only when the main thread has finished executing this piece of
// code inside the IIFE
setTimeout(function() {
console.log('Intended to be called after 200 ms delay, however called after the blocking completed');
}, 200);
// However the main thead is intentionally blocked here for 5 sec
// so the queued call can only happen post this IIFE has finished
// execution.
console.log('About to start 5 sec blocking');
var now = +new Date;
while(+new Date - now < 5e3); // simulating 5 sec blocking
console.log('blocking complete.');
})();
为了更好地了解队列和相关内容,我建议您观看What the heck is Event Loop
现在,回到你的问题,当你在i = 0
块中设置if(i == 4)
时,你无意中创建了一个无限循环。
因此,最终,您正在排队事件队列中的函数,但不会释放主线程。
因此,事件队列永远不会有机会执行。
function first() {
console.log('hello from first function');
}
function second() {
console.log('hello from second function');
}
function third() {
console.log('hello from third function');
}
function fourth() {
console.log('hello from fourth function');
}
function fifth() {
console.log('hello from fifth function');
}
var array = [first, second, third, fourth, fifth];
for (var i = 0, len = array.length; i < len; i++) {
if (i == 4) { i = 0;} // this causes infinite loop
console.log('I became an infinite loop');
// functions are added to the queue, but the main thread is stuck in an infinite loop
// hence cannot execute these timeouts
(function(i) {
setTimeout(function() {
array[i]();
}, 1e2*i);
})(i);
}
因此,您需要一种方法来打开和打开函数数组。这在我看来是递归的用例。 我希望你能轻松实现。