Pause loop for a second after every five iterations - javascript

For my program I have to make a 100 JSON requests. Unfortunately only 5 calls per second are allowed. Since I am making all the JSON request with a for loop (is the best way), I have to pause the loop after every 5 calls for 1 second.
function Hello() {
$("#randomdiv").show();
for (var i=0; i<100; i++) {
if (i%5 == 0 && i>0) {
sleep(1000);
}
$.getJSON(JSONreq, function(data) {Just a JSON request, nothing special})
};
};
The sleep(1000) causes the whole page to freeze for a about 20 seconds and prevents the #randomdiv from appearing before the JSON requests are made.
What can I do to solve this problem?
Thanks a lot :)

You can use a timeout with a closure:
function Hello() {
$("#randomdiv").show();
var loop = getLoop();
loop();
};
function getLoop() {
var count = 0;
var func = function() {
for (var i = 0; i < 5; ++i) {
$.getJSON(JSONreq, function(data) {Just a JSON request, nothing special})
}
if (++count < 20) {
setTimeout(func, 1000);
}
}
return func;
}

You can do something like this:
function Hello() {
$("#randomdiv").show();
for (var i = 0; i < 100; i++) {
var interval = 0;
if (i % 5 == 0 && i > 0) {
interval = 1000;
}
setTimeout(function () {
getJson()
}, interval);
};
}
function getJson() {
$.getJSON(JSONreq, function (data) {
Just a JSON request, nothing special
});
}

Related

clearInterval and set it again after x seconds

I want to do simple interval with with if, It is checking a variable's value and doing a function again().
again function contains clearInterval, i++ and setTimeout to call interval again after x seconds
var speed = 1000;
var wait = 0;
var i = 0;
function init() {
setInterval(function() {
if (i >= 6) i = 0;
if (i == 4) {
wait = 5000;
again(wait);
} else {
document.body.innerHTML = i;
i++;
}
}, speed);
}
function again(time) {
clearInterval(init());
i++;
setTimeout(function() {
setInterval(init(), speed);
}, time);
}
init();
I expect output like this:
1, 2, 3, Waiting x sec's , 5, 1, 2, ...
but code is doing some thing crazy, Its going faster and faster. I don't know why.
Here's a codepen with example (can crash your browser!)
Can you fix it and explain? Thanks
You are not clearing interval but use function inside clearInterval method. Method init which is used has no return statement so clearInterval gets undefined in attribute, so it is not clearing nothing.
Fixed code:
var speed = 1000;
var wait = 0;
var i = 0;
var interval=null;
function init() {
interval = setInterval(function() {
if (i >= 6) i = 0;
if (i == 4) {
wait = 5000;
again(wait);
} else {
document.body.innerHTML = i;
i++;
}
}, speed);
}
function again(time) {
clearInterval(interval);
i++;
setTimeout(function() {
init()
}, time);
}
init();
Function setInterval returns interval id and function clearInterval in attribute should get id of interval which we want to stop, so I created interval variable to save id. I am using this variable in clearInterval.
This is a small example how changing the delay of a setInterval call.
(function iife() {
var timer = null,
counter = 0;
function task() {
counter += 1;
console.log(counter);
// condition: every four reps
if (counter % 4 === 0) {
console.log("changed speed to 4 seconds");
return start(4000);
}
// condition: every seven reps
if (counter % 7 === 0) {
console.log("changed speed to 2 seconds");
return start(2000);
}
}
function start(delay) {
clearInterval(timer);
console.log("runs every " + delay + " miliseconds");
timer = setInterval(task, delay);
}
start(1000);
}());

Timed for loop in Javascript

I don't even know how to get started with this: I need a for loop that executes a function (say a simple console.log()) with a timed delay between each execution. I've been trying to do it with setTimeout() and it never works. If I call the function that has the loop from setTimeout, it won't work. Ideally I'd want my for loop to print something x times, with a couple of seconds delay between each printing. Any ideas how that might work? I've tried something like this:
function printStuff(){
for(var i=0;i<5;i++){
console.log(i);
}
};
setTimeout(printStuff(),1000);
For me you should execute setInterval and inside this you should increase counter. When counter reach the limit you simply clear interval.
var counter = 0;
var limit = 10;
var myVar = setInterval(function(){
if (counter > limit)
{
clearInterval(myVar);
}
counter++;
console.log("test");
}, 1000);
init();
function init() {
setTimeout(init, 2*1000); // wait 2 sec then call init again
console.log(Date());
}
Or use setInterval:
// Call init after 2 sec and repeat calling it every 2. sec
setInterval(init, 2*1000);
function init() {
console.log(Date());
}
You could use the async module.
var count = 0;
async.whilst(
function () { return count < 5; },
function (callback) {
count++;
console.log(count);
setTimeout(callback, 1000);
},
function (err) {
// 5 seconds have passed
}
);
This way the count will be printed every second
var i = 0;
function timeout(){
setTimeout(log, 1000);
}
function log(){
console.log(i++);
timeout();
}
log();
http://jsfiddle.net/sq4v0kbf/
Use setInterval() instead of setTimeout(). Parameters are just the same:
setInterval(function () {
// your utility code goes here
}, 2000);
Here is one more way to do it. Use a wrapper function.
var time = 2000;
for (var i = 0; i < 10; i++) {
(function (i) {
setTimeout(function () {
console.log(i);
}, time);
})(i);
time+=2000;
}
You can create a sort of delayed loop function with the number of iterations/times you want to run. Something like this:
var delayedLoop = function (n, milliseconds) {
var iteration = function (n) {
if (n > 0) {
n--;
console.log(n);
setTimeout(function () {
iteration(n)
}, milliseconds);
}
};
iteration(n);
}
delayedLoop(4, 1000);
You could even expand the idea and even passing a function to be executed each time.
See demo.
Here's what I think is simpler (and doesn't have the fallbacks of) than a setInterval
var limit = 10,
counter = 0,
delay = 1000;
function doIt() {
document.body.innerHTML += 'Hit counter: ' + (counter++) + '<br />';
if (counter < limit) {
setTimeout(doIt, delay);
}
}
doIt();
And you can generalize it
function runTimedLoop(delay, howMany, callback) {
var index = 0;
function iteration() {
callback(index++);
if (index < howMany) {
setTimeout(iteration, delay);
}
}
iteration();
}
runTimedLoop(1000, 10, function(index) {
document.body.innerHTML += 'Hit counter: ' + (index++) + '<br />';
});

Stop command is excuting from web browser console

i would like to execute a loop in chrome console ,but i want to stop it when it is running (without closing web browser).So how to do that . Thanks much for any helps .
This is my script ,i want to stop this:
for(var i=0;i<20;i++) {
(function (i) {
setTimeout(function () {
{
scrollBy(1500, 999999);
}
}, 8000 * i);
}(i));
};
setTimeout(function () {
alert('Finish--------------!');
}, 8000 * (i));
Correct me if I'm wrong but I think you're trying to clear the timeout objects rather than stop the loop.
Try something like this:
var obj = [];
for(var i=0;i<20;i++) {
(function (i) {
obj.push(setTimeout(function () {
{
scrollBy(1500, 999999);
}
}, 8000 * i));
}(i));
}
obj.push(setTimeout(function () {
alert('Finish--------------!');
}, 8000 * (i)));
// when this function is called it will loop over the timeout objects
// you created in the above loop and clear them
function clearTO() {
var i;
for (i = 0; i < obj.length; i += 1) {
clearTimeout(obj[i]);
}
}
// if typing 'yes' in the prompt gives you the behavior
// you're looking for replace this timeout function with something more dynamic that fits your needs
var cnt = 0;
function stop() {
if (prompt("type yes to stop") === "yes") {
clearTO();
} else if(cnt < i){
cnt += 1;
setTimeout(stop, 8010);
};
}
stop();
Obviously You'll have to bind clearTO() to an event of some kind.
Maybe try this another function structure:
eg.
//CODE WILL STOP WHEN PAGE IS NEARLY END
var i=0;
function someFunc() {
setTimeout(function () {
{
scrollBy(0, 200);
}
}, 8000 * i);
i++;
if($(window).height()-window.pageYOffset < 200) i=20;
if(i<20) someFunc();
}
someFunc();

setTimeout in Winjs

Regarding to servers API, i should limit requests to 3 per second.
Here is my code:
groups.forEach(function (group) {
Api.simpleRequest(uri).then(function (res){
// processing result
}, function(err) {
// error handling
});
});
What i tried to do:
1.
for (var i=0; i < groups.length; i++) {
(function (index){
setTimeout(function() {
Api.simpleRequest(url).then() //...
}, 1000);
})(i);
};
Tried to use WinJS.Promise.timeout(1000) as then continue of my promise.
Both options does not work for me.
Just found working solution, but with setInterval() instead of setTimeout()
var i = 0;
var length = groups.length - 1;
var timer = setInterval(function() {
Api.simpleRequest(uri).then() //...
if (i == groups.length) {
clearInterval(timer);
};
i++;
});

JavaScript Worker : how to check if a message was received while running expensive task

I have a very expensive task running on a Worker, similar as this
for(var i = 0; i < 1000000000; i++)
//operations using i...
How can I make is so that, in that loop, I can check if a message was received from the Worker owner asking it to stop? I would like to have something like this
for(var i = 0; i < 1000000000; i++)
if(windowDidNotAskToStop())
//operations using i...
Right now I have a onmessage function registered so I can start listen to message coming from the owner, but it is blocked while my loop is running (obviously).
I imagine that the postMessage calls from the owner are queued somewhere, so I would simply have to access that in order to process the calls from inside my loop.
You’ll have to handle the events as usual and set a flag, but make sure to leave time for the event to be received in your loop, probably using setTimeout:
var exitLoop = false;
(function loop(i) {
if (exitLoop || i >= 1000000000) {
return;
}
// …
setTimeout(function () {
loop(i + 1);
}, 0);
})(0);
onmessage = function (e) {
if (e.data === 'stop') {
exitLoop = true;
}
};
Or, as a general utility function:
function asyncIterateRange(start, end, callback) {
var exitLoop = false;
var doneCallbacks = [];
(function loop(i) {
if (exitLoop) {
return;
}
if (i >= end) {
doneCallbacks.forEach(function (callback) {
callback();
});
return;
}
callback(function () {
setTimeout(function () {
loop(i + 1);
}, 0);
});
})(start);
return {
abort: function abort() {
exitLoop = true;
},
done: function addDoneCallback(callback) {
doneCallbacks.push(callback);
}
};
}
Use it like so:
var innerIterator;
var outerIterator = asyncIterateRange(0, 1000000, function outerLoop(next) {
innerIterator = asyncIterateRange(0, 1000, function innerLoop(next) {
// …
next();
}).done(next);
});
// To stop:
if (innerIterator) {
innerIterator.abort();
}
outerIterator.abort();

Categories

Resources