The sixth edition of ECMAScript (also known as ECMAScript 2015 or simply ES6) was officially published in June 2015. It is the most significant update of the language for the last 16 years. It adds new significant syntax update, that makes JavaScript code look cleaner and more object oriented than ever before. At this moment browser support for ES6 is still incomplete. However, ES6 code can be compiled into ES5 code, that supported by majority of browsers.
In this series of posts we will take a closer look at new syntax and features that ES6 brings to JavaScript. And we start with new let ans const keywords.
1. let vs var
As you know ES5 has only two scopes: local scope and global scope. If you declare a variable inside function, it will have local scope: it can be accessed only within the function. Variable declared outside of a function have global scope. It can be accessed from any place in the application.
ES6 ads one more scope: block scope. A variable declared inside some block of code enclosed by curly braces has block scope. It’s only visible within that block of code and cannot be accessed from outside of that block.
If statement, loops, functions e.t.c, all these are considered as blocks of code. ES6 uses let keyword to define a variable with block scope.
Let’s look at the following example.
using var:
1 2 3 4 5 |
if (true) { var keyWord = "VAR"; } console.log(keyWord); // => VAR |
The variable keyWord is declared inside of the if block using keyword var. It can be accessed from outside of the block and we can print it on the console.
using let:
1 2 3 4 5 |
if (true) { let keyWord = "LET"; } console.log(keyWord); // => Throws an error: Uncaught ReferenceError: language is not defined |
The keyWord variable is declared inside of the if block using keyword let. We can not access the variable from outside of the block. If we try to print it from outside of the block it throws an exception.
This is how block scoping works in ES6.
Unlike var, let does not allow you to access variable before it’s declared . Let’s take a look at the following peace of code:
1 2 |
console.log(language); // => Throws an exception: Uncaught ReferenceError: language is not defined let language = "JavaScript"; |
If you try to access a variable (print this variable in the console in this case ) before it’s defined with let key word, it will throw an error. Let’s take a look at how it works with var keyword.
1 2 |
console.log(language); // => undefined var language = "JavaScript"; |
It does not throws an exception and prints undefined in the console. This works because JavaScript engine puts declaration of all variables with var keyword in the beginning of the code. So even you declare a variable after using it, the JS engine will fix it for you and behind the scene it would look like this:
1 2 3 |
var language; console.log(language); // => undefined language = "JavaScript"; |
Let’s look at one more example.
See the Pen mROKxm by Pavel Terenin (@PavelT) on CodePen.
In this example we have 5 buttons in HTML file. In JS file we iterate through each of the buttons using for loop. Inside of the loop we give a number to each button and when we click one of them we would like to see a message with the number of the button. For example when we click button #3 we would like to see “Button #3” message. The example is interactive, please try to click buttons.
As you see it does not work as we expected. It always shows message “Button #5“, no meter what button we click. This happens because we use var keyword in this line:
1 |
for (var i = 0; i < buttons.length; i++ ) |
It means variable i is global and it changes it’s value as we go through the loop. In the end it will have value, that was given to it in the last iteration.
Let’s change var keyword to let.
1 |
for (let i = 0; i < buttons.length; i++ ) |
This way we will limit scope of i variable to block of code. In this case it’s a block of the for loop. The variable is locked to each iteration of the loop and we will have right result:
See the Pen jyVvOq by Pavel Terenin (@PavelT) on CodePen.
2. Using const
Besides let ES6 introduced one more new keyword – const. const stands for constant. Constant – is a variable that can’t change it’s value after it’s declaration. A variable declared with const has a block scope and works much like variables declared with let. But unlike let the value of a constant can not be changed .
Let’s take a look to the following example.
1 2 3 4 5 6 7 8 9 10 |
//var and let variables can change var language = "JavaScript"; language = "C#"; //works let OS = "Windows"; OS = "Mac OS"; // works as well //const variables can not change const browser = "Chrome"; browser = "Opera" //throws an exception: Uncaught TypeError: Assignment to constant variable. |
Unlike let and var you cannot declare a constant without a value:
1 2 3 |
var langauge; //works. value is undefined let OS; //works. value is undefined const browser; //Uncaught SyntaxError: Missing initializer in const declaration |
const also works with objects and arrays.
1 2 3 4 5 |
const person = {name: "Bill", age: 32}; person = {name: "Peter", age: 37}; //Uncaught TypeError: Assignment to constant variable. const numbers = [1,2,3]; numbers = [10, 20, 30]; //Uncaught TypeError: Assignment to constant variable. |
However objects are not fully protected by const. We still can change properties of the object .
1 2 3 |
const person = {name: "Bill", age: 32}; person.name = "Peter"; //works console.log(person); // => {name: "Peter", age: 32} |
So as we see const does not make objects immutable. The same happens with arrays. You can not reassign it, but you can add, remove, reorder and modify elements:
1 2 3 4 5 6 |
const numbers = [1,2,3]; numbers[1] = 222; numbers.push(4); numbers.shift(); console.log(numbers); //=> [222,3,4] |
If you do need to make an object immutable, you can use Object.freeze method. It’s not ES6 method, you can take a look at how it works on MDN. It does not allow any changes.
1 2 3 |
const person = Object.freeze({name: "Bill", age: 32}); person.name = "Peter"; console.log(person); // => {name:"Bill", age: 32} |
1 2 3 4 5 6 7 |
const numbers = Object.freeze([1,2,3]); numbers[1] = 222; //does not throw an error but value is not changed console.log(numbers); //=> [1,2,3] numbers.push(4); //throws an exception numbers.shift();//throws an exception |
This way we can make objects and arrays fully immutable.
Conclusion
You are probably wondering what keyword you should use in your application. I have a suggestion: use const as much as possible. It makes you code more robust. If you expect that your variable is going to change during program execution – use let. So what’s about var? The reality is that when you write ES6 code and you want your code to be robust and easy to debug you don’t really need var. R.I.P. var, you will be missed.
Pingback: vioglichfu.7m.plindex.php?n=25()