Global Block Bindings
Another way in which let
and const
are different from var
is in their global scope behavior. When var
is used in the global scope, it creates a new global variable, which is a property on the global object (window
in browsers). That means you can accidentally overwrite an existing global using var
, such as:
// in a browser
var RegExp = "Hello!";
console.log(window.RegExp); // "Hello!"
var ncz = "Hi!";
console.log(window.ncz); // "Hi!"
Even though the RegExp
global is defined on window
, it is not safe from being overwritten by a var
declaration. This example declares a new global variable RegExp
that overwrites the original. Similarly, ncz
is defined as a global variable and immediately defined as a property on window
. This is the way JavaScript has always worked.
If you instead use let
or const
in the global scope, a new binding is created in the global scope but no property is added to the global object. That also means you cannot overwrite a global variable using let
or const
, you can only shadow it. Here’s an example:
// in a browser
let RegExp = "Hello!";
console.log(RegExp); // "Hello!"
console.log(window.RegExp === RegExp); // false
const ncz = "Hi!";
console.log(ncz); // "Hi!"
console.log("ncz" in window); // false
Here, a new let
declaration for RegExp
creates a binding that shadows the global RegExp
. That means window.RegExp
and RegExp
are not the same, so there is no disruption to the global scope. Also, the const
declaration for ncz
creates a binding but does not create a property on the global object. This capability makes let
and const
a lot safer to use in the global scope when you don’t want to create properties on the global object.
I> You may still want to use var
in the global scope if you have a code that should be available from the global object. This is most common in a browser when you want to access code across frames or windows.