3

I understand the behavior of using var and let in for loop in typescript/javascript but can someone explain why and how a const variable as a loop variable behaves ?

for (const i = 0; i < 5; i++) {
  setTimeout(function() {
    console.log(i)
  }, 100 * i);
}

From what i understand , when you declare a variable as const and initialize its value , the value cannot be changed

Yet you can see the value being changed in the console.log() .An error has to be thrown while compilation right ?What am i missing here ?

I have created 2 examples for this behavior .

Loop variable as a const

Const variable re assignment

Can someone help me understand this ?

6
  • 1
    bothconst and let have block scope and is hoisted at the top of the block its defined in, the only difference between const and let is variables declared const cannot be reinitialized Commented May 9, 2019 at 11:56
  • 1
    Please include all code in the question itself, not only on an external site. Commented May 9, 2019 at 12:01
  • 3
    @messerbill a real ES2015 environment does actually have constants. Commented May 9, 2019 at 12:04
  • 1
    @HereticMonkey i would have included the code but i wouldn't be able to show the behavior if it wasn't a stackblitz example . I hope you understand where i'm getting at Commented May 9, 2019 at 12:17
  • 1
    If that was the case, and you know the behavior was only replicable in Stackblitz, then you should mention that in the question. Commented May 9, 2019 at 12:21

2 Answers 2

7

It works in Stackblitz because it is running traspiled code:

AppComponent.prototype.test = function () {
    var _loop_1 = function (i) {
        setTimeout(function () {
            console.log(i);
        }, 100 * i);
    };
    for (var i = 0; i < 5; i++) {
        _loop_1(i);
    }
};

It won't work if you add a snippet here because it is not transpiled

for (const i = 0; i < 5; i++) {
  setTimeout(function() {
    console.log(i)
  }, 100 * i);
}

enter image description here

Sign up to request clarification or add additional context in comments.

3 Comments

looks like i shouldn't trust stackblitz much or i don't understand how stackblitz works . Thanks a lot for clearing the doubt .so i was correct in assuming that the loop will break.
@CruelEngine tbf, it does show the red squiggly line under i++ with error message: "Cannot assign to 'i' because it is a constant or a read-only property."
and yet it compiled and that is where i was a bit confused
0

Answering your question,

  test(){
    for(const i =0 ; i< 5; i++){
      setTimeout(function(){
        console.log(i)
      },100*i);
    }
  }

This code essentially becomes,

  test(){

    // can be only initialized once
    const i;
    for(i = 0 ; i< 5; i++){
      setTimeout(function(){
        console.log(i)
      },100*i);
    }
  }

Because every JavaScript variable is hoisted at the top of its scope, in this case the test() as its const variable that's why its hoisted in that block and not accessible outside of it.

To correct the piece of the code:

  test(){

    // can be only multiple times in that block
    for(let i = 0 ; i< 5; i++){
      setTimeout(function(){
        console.log(i)
      },100*i);
    }
  }

Which becomes,

  test(){

    let i;
    // can be only multiple times in that block
    for(i = 0 ; i< 5; i++){
      setTimeout(function(){
        console.log(i)
      },100*i);
    }
  }

As both const and let have block scope and is hoisted at the top of the block its defined in, the only difference between const and let is variables declared const cannot be reinitialized.

4 Comments

hoisting has nothing to do with this behavior right ? the loop should never run if i declare the loop variable of const
@CruelEngine you cannot increment a const variable once initialized
yes exactly and yet the code ran in the example i attached in the question
@CruelEngine I think webpack is transpiling the code to ES3 to maintain compatibility which didnt had const and let and the const is converted to var. Anyway you can inspect the transpiled file in the dist folder.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.