In the early days, var keyword is used usually to define a variable, but it would bring some troubles, such as variable obfuscation and memory leaks about variable.
Variables defined by var are declared at the top of their scope in advance and assigned the value underfined regardless of where they are declared.
After ES6, let and const keyword appeared while block scope was introduced. Block scope is differentiated by { }, so if, for, while, etc all have their own block scope, but must use let, const keyword declared variables and var hasn't block scope yet.
At the same time, let, const haven't also hoisted-variable as var do.