FAQ: Scope - Scope Pollution

as a follow up, i did some reading on this thread scope - Javascript local variable is overriding global variable? - Stack Overflow

apparently, in JS the only way to create a local variable that won’t affect a global variable of the same name is by using the “let” keyword inside your function. hope this helps others…

2 Likes

Hi, I have problem understanding this sentence: “These variables remain there until the program finishes which means our global namespace can fill up really quickly.”
what does it mean for the namespace to be filled up? does it run out of memory? I can’t understand.
Thanks in advance for the attention you give to this question.

unlikely.

Having a lot of variable in the global namespace, might result in accidentally re-assigning an already defined/named variable

or: Becomes more difficult to give a good name to variable because the name already exists/is already taken

2 Likes

Here’s what I don’t understand. In both the example in the lesson AND in the exercise, we can avoid overwriting our global variable simply by using the let keyword within our function:

const satellite = 'The Moon';
const galaxy = 'The Milky Way';
let stars = 'North Star';

const callMyNightSky = () => {
  let stars = 'Sirius'; // notice the let keyword here!
  return 'Night Sky: ' + satellite + ', ' + stars + ', ' + galaxy;
};

console.log(stars); // prints: North Star - the global variable did NOT get overwritten

With that being said, what’s the argument for avoiding global variables when possible, as the lesson suggests? It seems like the whole “scope pollution” thing is a non-issue if you just remember to use the let keyword within your functions.

Can anyone weigh in? If scope pollution can be so easily avoided, why is it a “best practice” not to define variables globally?

While scope pollution is avoidable, it is still a consequence of coding errors, nonetheless. It is a checkpoint on the debugging check list. All variables properly scoped? Check.

This is obviously less about a best practice that one should adopt not because it is best, but for the reasons laid out. Undeclared variables are hoisted to global scope, thereby polluting the namespace and causing avoidable collisions. Bear in mind that before ‘modules’ came on the scene, everything, and that is everything shared the one global namespace. Potential for collisions was ever present. Modules change that by creating external namespaces, but it doesn’t correct the inherent problem. Just makes it all the more simple to avoid. Another story.

Hello, I have a question that seems very basic, however I can’t find another instance in this thread of someone else asking it. Or if they have they are using terms that don’t make sense to me.

In the previous page before Scope Pollution we are told about Block Scope. The resource says:
" When a variable is defined inside a block, it is only accessible to the code within the curly braces {}.".

This seems clear to me, however immediately after in the Scope Pollution lesson we are given an example where the opposite seems to apply, with the block variable affecting the pre-established global variable, using code outside of the block. Since the language in the previous statement is so clear (and is not expanded upon further) I’m not sure what I’m missing. Even the example codes given seem to contradict each other. (I can give examples but I feel the simplicity renders them unneccessary).

I’d appreciate if someone has the know-how to enlighten me!
Thanks
https://www.codecademy.com/courses/introduction-to-javascript/lessons/scope/exercises/global-scope-ii

lets look at the example:

let num = 50;
 
const logNum = () => {
  num = 100; // Take note of this line of code
  console.log(num);
};
 
logNum(); // Prints 100
console.log(num); // Prints 100

this is totally fine? Given num is within the scope, we can update/re-assign the variable.

now, things change when we decide to declare a new variable with the same name within the function:

let num = 50;
 
const logNum = () => {
   // added let here
  let num = 100; // Take note of this line of code
  console.log(num);
};
 
logNum(); // Prints 100
console.log(num); // Prints 50

now we declare a new variable within the function, with its own scope rules

There is a difference between declaring variable (when we set the scope with let) or re-assigning an existing variable

Thanks stetime94 for clarifying the difference in this example between declaring and re-assigning an existing variable.

I think I am starting to understand, although I feel that the language in the lesson may have misled me a bit. It says " Variables that are declared with block scope are known as local variables because they are only available to the code that is part of the same block".

However in your first example, when logging “num” to console you are accessing the re-assigned variable from the block, which seems to be counter to the statement quoted above. Is this because the function has been called on the previous line?

Thanks again.

to declare a variable with a block, you need to use let or const keyword

here:

  num = 100; // Take note of this line of code

you do not declare a variable, you re-assign an existing variable

It finally clicked! Thank you for breaking it down completely stetime94, it was a great help.

Would it be good practice to make all global variables const? That way you can’t accidentally change them.

generally yes, but there might be cases where you actually want to update global variable. So then const is not recommended

If you have a lot of global variable, this is generally also an indication that your code needs a review/refactor

unfortunately, absolutes (like declaring all global variable as constant) rarely works in programming

1 Like