I have the following code:

$(document).ready(function() { ... function funcA(items) { // Ранее этого места index нигде не фигурирует. for (index = 0; index < items.length; index++) { var a = funcB(items[index]); ... } } } function funcB(id) { for (index = 0; index < initJson.length; index++) { item = initJson[index]; if (item.id == id) { return item; } } return -1; } 

In the funcA function and the funcB function funcB I use variables in the loop with the same name ( index ), which at first glance are completely unrelated to each other, since they must exist in different “visibility spaces”. Using the debugger, I see that the value of the index variable in the funcA function, after calling funcB becomes equal to the last value in the funcB function. Tell me why I see this behavior? Behavior does not occur if, in a loop, I declare a variable as var index = 0 , yet it is not clear how and why the variable from the scope of the calling code falls and changes in the callee.

  • one
    because the construct index = 0 without var creates a global variable - Duck Learns to Cover February
  • @ Duck Teaches Mind Absolutely always and even inside a function? - Nicolas Chabanovsky
  • not "absolutely always", in strict mode does not create, but simply swears at this. Well, of course, if the index was previously declared (somewhere in the body of the function, var index is made;) it does not create - Duck Learns to Take Cover
  • one
    @ DuckToKeUmu I would be extremely grateful to you for a detailed answer! - Nicolas Chabanovsky
  • I must now admit that laziness, the whole section of the specification is devoted to the creation of variables ( ecma-international.org/ecma-262/7.0/… ), and Grundy answered exactly for sure somewhere, you have to wait for it to appear. I would also recommend using let indexes for loops indexes as much as possible, this will save you from potential problems with understanding closures) - Duck Learns to Take Cover

2 answers 2

The scope is created by functions and modules (like IIFE via the script tag (whether the code is loaded or which is inside)) and ES6 modules.
A relatively new standard heard the tears of developers and introduced block visibility ( {} ) through let , const .

Announcement via var write the variable to the nearest external area.
Ads without var written in the window (it is not known what the creators were guided by, but, apparently, there was a lot of crap). This phenomenon is cut by an error in strict mode.

let , etc. are limited to the nearest external unit.

Knowing this, you can understand that your code uses the same variable.
Fill in any available visibility modifier and it would work:

 function a(){ // Без указания видимости, в window b = 41; } a(); console.info(b, window.b === b); // 41, true function a(){ // В видимость функции var b = 42; } a(); console.info(b); // ReferenceError: b is not defined 

Block visibility:

 function a(){ let b = 42; { let b = 41; } console.info(b); // 42 } a(); 

  • Generally speaking, modules and a separate script tag are not the same - Grundy
  • So I wrote (in brackets just more about the definition (which is not about import/export )). - user207618
  • one
    then where are the modules? script tags do not create a separate scope :) - Grundy
  • Hmmm, like create. From one you can’t get visibility into another tag. - user207618
  • You try :-) - Grundy

As already mentioned, no var creates a global variable. So it is arranged, therefore, if you declare a variable inside a function and you want it to be visible only in the function, then do it through var, then its scope will be limited to this function.

The scope is well described here.

  • Thanks for the answer. Could you add a minimal example to your answer that would clearly show what was happening. - Nicolas Chabanovsky
  • I would love to, but this is already later, since not at the computer. According to the link that I added there are examples and tasks. In general, I advise you to go through this tutorial - this is a very good alternative to books, but without books, nowhere. - Vladyslav Tereshyn