You though the first argument passed to setTimeout is a function, but it's not.
When you do:
setTimeout(hi(x), 100000);
it means:
- evaluate the expression
hi(x) to get its value
after 100000ms, if the value from previous step is
- callable, call it (with arguments if passed)
- otherwise evaluate it (similar to
eval)
so it equals:
var ret = hi(x);
setTimeout(ret, 100000);
Apparently ret is not your function hi, but the return value of it - undefined. So setTimout(undefined, 100000) actually does nothing meaningful - eval(undefined) after 100000ms.
Strip that out, your code equals:
(function hi(x) {
if (x > 1000) {
return;
} else {
x+=1;
hi(x);
console.log(x);
}
})(4)
What's this? Yes, synchronous recursive function call. That's why you see the result in console is counting down rather you expected.
The solutions, besides wrapping it in an anonymous function:
setTimeout(function () {
hi(x);
}, 100000);
Alternatively you can also pass extra arguments to setTimeout:
setTimeout(hi, 100000, x);
Arguments passed to setTimout after the delay, will be passed in hi when invoking it.
console.log(x)statement before thesetTimeoutcall to help you visualise what happens.