Understanding var, let and const keywords and using them in the right way

Posted on February 01, 2021


Since ES2015, JavaScript has released two more keywords as an alternative to var. They are let and const keywords. These two keywords are included in JavaScript to fix some weird behaviors of var keyword that have been causing errors when building JavaScript applications.

To understand the differences between var, let, and const, you need to learn more about var first.

The weird behavior of var keyword

As you may know, the var keyword is used in JavaScript to declare and initialize a variable. You declare a variable when you assign a variable name, but you don’t assign any value to it:

var declare;

Then you can initialize your variable by assigning a value to it:

declare = "Initializing variable";

You can do both at the same time too:

var declared = "Initialized";

Now here are some problems with the var keyword.

Variable re-declaration

First, you can re-declare a variable with the same name, even though it will cause duplicates:

var declared = "Initialized";
var declared = "This is also initialized";
console.log(declared); // This is also initialized

The expected outcome of the code above is that the second line should throw an error because you can’t have two variables with the same name. But instead of throwing an error, JavaScript will simply re-assign your variable value with the second declaration’s value.

The let keyword fixes this behavior by throwing an error when you declare a variable with a used name:

let declared = "Initialized";
let declared = "This is also initialized"; // SyntaxError: Identifier 'declared' has already been declared

Variable hoisting

Hoisting is JavaScript’s built-in behavior to secretly define all declarations at the top of the scope. This helps you to call on variables and functions before you initialize them:

myFunction();

function myFunction() {
  console.log("Hello world!");
}

But while hoisting is good for functions, it’s actually bad for variables because you shouldn’t be able to call on variables before you initialize them. The following variable declaration:

console.log(x); // undefined
var x = 7;

Is actually executed like this by JavaScript:

var x;
console.log(x); // undefined
x = 7;

The let keyword fix this behavior by throwing an error when you try to access the variable before initialization:

console.log(x); // ReferenceError: x is not defined
let x = 7;

Variable scoping

In general, variables in programming languages are expected to be scoped inside the block where it was declared and initialized. A block is simply a piece of code bounded using curly braces ({}). You commonly create code blocks when you use if, switch, for, while, and so on.

The following is an example of an if block:

if (true) {
  // the if block here
}

And here’s a function block:

function sum() {
  // function block here
}

Now here’s the problem: variables declared with var can be accessed outside the block scope, but not outside of the function.

The code below should have caused an error:

if (true) {
  var x = 7;
}
console.log(x); // 7

But var can’t be accessed outside the function:

function sum() {
  var x = 7;
}
console.log(x); // Error: x is not defined

As you can see, the var keyword has inconsistent scoping because it’s either global or function-scoped, when it should’ve been block scoped.

The let keyword has fixed this behavior by throwing an error when you declare the variable inside any block, whether it’s an if statement or a function statement:

if (true) {
  let x = 7;
}
console.log(x); // Error: x is not defined

By using let keyword, your variable will be limited to the block it was declared and initialized.

What about const?

The const keyword is the same as let keyword with two extra rules:

  • variables declared with const must be initialized / assigned a value
  • variables declared with const can’t be re-assigned another value after initialization

So you can’t declare a variable with const like this:

const declare; // Error

You must initialize the variable immediately after declaration:

const declare = "Initialized";

And you can’t change the value after that:

const declare = "Initialized";
declare = "Change the value"; // Error

In other words, the const keyword is used to create a variable with a constant (fixed) value. It stays the same throughout the lifetime of your JavaScript application.

Conclusion

To conclude, here are the differences between var, let, and const keywords:

  • The var keyword can be re-declared, let and const won’t allow you to do it.
  • All three are hoisted to the top of their scope, but var is initialized with undefined as value while let and const are not initialized at all.
  • The var keyword has inconsistent scoping, let and const are always block-scoped.

The var keyword should stop being used in new projects, and you should declare a variable using let by default. Only use const for variables with fixed values. Ideally, you should have lots of let keywords and fewer const with no var.

But you will definitely find lots of var keywords in old projects, so you should schedule a time to refactor them into let if you can.

Bonus weird part on JavaScript

Here’s another weird behavior of JavaScript. It allows you to initialize a variable without declaring a variable with var keyword:

declared = "Initialized";
console.log(declared);

In other programming languages, this should lead to an error because declared is not defined. Unfortunately, you can’t fix this problem with either let or const keywords. You need to use the use strict JavaScript directive.

"use strict";
declared = "Initialized";
console.log(declared); // error here

The strict mode will turn all bad syntax of JavaScript into real errors.

More on JavaScript:

Grab the free JavaScript book today 👍

Learn the building blocks of JavaScript programming language like data types, functions, objects, arrays and classes.

Use the knowledge from the book to build a small but solid program.

Learn more