0

Why the following code returns 10 times 10 and print hey as first line?

   for (var i = 0; i < 10; ++i) {
      setTimeout(() => console.log(i), 0)
    }
    console.log('hey')

When if instead I use let I get properly the counting, but why the line hey is always printed first?

 for (let i = 0; i < 10; ++i) {
      setTimeout(() => console.log(i), 0)
    }
    console.log('hey')

My question actually contains two:

  • First why hey is printed first.
  • Why using let the counting is printed properly.
Radex
  • 7,815
  • 23
  • 54
  • 86
  • Not sure if this answer my question, also does not cover setTimeout – Radex Aug 15 '17 at 17:28
  • There's nothing special about `setTimeout`. The difference is just in whether each closure gets the same or a different binding of `i`, which is because of the difference between the scopes of `let` and `var`. – Barmar Aug 15 '17 at 17:29
  • Doesn't matter, the timeout is irrelevant here, the reason it works is because `let` is block scoped and works in the "infamous closure inside loop" issue – adeneo Aug 15 '17 at 17:29
  • Why is that a duplicate? He's asking why the different position of `Hey` in the two examples. It would seem like `hey` should always be printed before the `setTimeout` callbacks. – spanky Aug 15 '17 at 17:29
  • @spanky He's asking two questions. The difference between `let` and `var` is in the title, so that's presumably his main question, and the other was an aside. – Barmar Aug 15 '17 at 17:30
  • I see. Well the "aside" seems more interesting. I thought that even with a `0` timer, there should still be async behavior. Maybe the console is async too? – spanky Aug 15 '17 at 17:31
  • maybe related? https://stackoverflow.com/questions/31285911/why-let-and-var-bindings-behave-differently-using-settimeout-function – Radex Aug 15 '17 at 18:44

1 Answers1

0

setTimeout() is an asynchronous function

console.log('hey') 

won't wait for it to finish before printing, since JS is single threaded, it would wait for the program to run and then pick the setTimeout() from event queue

difference between let and var can be found in this answer. Basically since let has scope limited to the for loop, the setTimeout can refer to only 1 value of i. If we use var then it is function scope and each function would get the same value of i

marvel308
  • 10,288
  • 1
  • 21
  • 32