var
vs let
vs. const
. What's the Difference?
To analyze the differences between these keywords, I'll be using three factors:
- Scope of variables
- Redeclaration and reassignment
- Hoisting
Var
- Variables declared with
var
can have a global or local scope. - Global scope is for variables declared outside functions, while local scope is for variables declared inside functions.
- Variables declared with
var
can be redeclared and reassigned. - Variables declared with
var
are hoisted to the top of their global or local scope, which makes them accessible before the line they are declared. But the variable is hoisted with a default value of undefined.
var a = 100;
let b = 200;
const c = 300;
{
var a = 1; // a is shadowing 'a' in line 1 (both 'a' are pointing to same memory location) // GLOBAL memory
let b = 2; // block memory
const c = 3; // block memory
console.log(a); // 1
console.log(b); // 2 // shadowing because of block memory
console.log(c); // 3 //
}
console.log(a); // 1 shadowed and modified line 1, both 'a' are pointing to same memory location)
console.log(b); // 200 // Not shadowing because of block memory, diff memory space
console.log(c); // 300 // Not shadowing because of block memory, diff memory space
Let
- Variables declared with
let
can have a global, local, or block scope. - Block scope is for variables declared in a block. A block in JavaScript involves opening and closing curly braces.
- Just like
var
, variables declared withlet
can be reassigned to other values, but they cannot be redeclared. - Redeclaring a variable with let will throw an error. You see we get a syntax error: Identifier 'number' has already been declared.
var a = 100;
let b = 200;
const c = 300;
{
var a = 1; // a is shadowing 'a' in line 1 (both 'a' are pointing to same memory location) // GLOBAL memory
let b = 2; // block memory
const c = 3; // block memory
console.log(a); // 1
console.log(b); // 2 // shadowing because of block memory
console.log(c); // 3 //
}
console.log(a); // 1 shadowed and modified line 1, both 'a' are pointing to same memory location)
console.log(b); // 200 // Not shadowing because of block memory, diff memory space
console.log(c); // 300 // Not shadowing because of block memory, diff memory space
Const
- Variables declared with
const
are similar tolet
in regards to scope. Such variables can have a global, local, or block scope. - In this regard,
const
is different fromvar
andlet
.const
is used for declaring constant variables – which are variables with values that cannot be changed. - So such variables cannot be redeclared, and neither can they be reassigned to other values. Attempting such would throw an error.
- SyntaxError: Identifier 'number' has already been declared
- TypeError: Assignment to constant variable
- Variables declared with const, just like let, are hoisted to the top of their global, local, or block scope – but without a default initialization.
- Accessing a variable declared with const before the line of declaration will throw a cannot access variable before initialization error.
- ReferenceError: Cannot access 'number' before initialization
var a = 100;
let b = 200;
const c = 300;
{
var a = 1; // a is shadowing 'a' in line 1 (both 'a' are pointing to same memory location) // GLOBAL memory
let b = 2; // block memory
const c = 3; // block memory
console.log(a); // 1
console.log(b); // 2 // shadowing because of block memory
console.log(c); // 3 //
}
console.log(a); // 1 shadowed and modified line 1, both 'a' are pointing to same memory location)
console.log(b); // 200 // Not shadowing because of block memory, diff memory space
console.log(c); // 300 // Not shadowing because of block memory, diff memory space
Summary
Here's a table summary showing the differences between these keywords:
KEYWORD | SCOPE | REDECLARATION & REASSIGNMENT | HOISTING |
---|---|---|---|
var | Global, Local | yes & yes | yes, with default value |
let | Global, Local, Block | no & yes | yes, without default value |
const | Global, Local, Block | no & no | yes, without default value |
These factors I've explained, play a role in determining how you declare variables in JavaScript.
If you never want a variable to change, const
is the keyword to use.
If you want to reassign values:
- and you want the hoisting behavior,
var
is the keyword to use - if you don't want it,
let
is the keyword for you
The hoisting behavior can cause unexpected bugs in your application. That's why developers are generally advised to avoid var
and stick to let
and cost
.