Variable scope question

I have a for loop where I define a var i

That loop is done with, and now I need another. If I code

for ( i = 0; i < ....etc.

The warning yellow triangle appears, saying “i used out of scope.” I thought JS doesn’t have block scope - but anyway if I declare it:

for ( var i = 0; i < ....etc.

the yellow triangle then says “i is already defined.” Seems it can’t get no satisfaction.

Not fatal, but what’s behind this and what’s best practice?

Thanks

If you use let i = 0, it’s scope will be limited to the scope of the for-loop (i.e., it’s block-scoped). Note that let is ES6, so you might have to use Babel.

Hi Roy,

No expert on scope, but I think if both your loops are within the same function (or there is no function wrapping either of them at all) than the i variable is visible to both loops. Without the var keyword the scope is global as you know, and with the var keyword its local. If both loops are in the same function then you will need to use another letter (i usually go j) as you would when nesting loops inside each other.

This is just a JS Hint warning. As the others pointed out, avoid the gloabal declaration.

I don’t know if it’s best practice, but I use the method @MARKJ78 for nested loops (i, then j (if you need more letters that’s usually a sign to refactor!)), but I think you should be ok re-using i as your counter for unrelated loops in the same function - except for JS Hint complaining.

You can tell JS Hint to shut up: http://stackoverflow.com/questions/25102262/is-there-a-way-to-silence-jshints-variable-is-already-defined-warning

Thanks folks.

They were in the same function, yes. I recognized at as just a warning, but was curious as to why the warning messages contradicted and didn’t want to set up a new variable. I guess hinting can’t see that the loops are separate and independent, so I’ll go with another letter.

I’ll stay away from ES6 for now, as I don’t know how to use Babel inside a freeCodeCamp challenge (or even outside, come to that).

I’m pretty sure you can’t, but chances are ES6 features will work (you’ll get some warnings though)