What is the use of hoisting in JavaScript?

5

Before ES6, all variables in a function were created independently of JS scope. That is:

if(false) {
  var mensagem = "Olá!"; // declaração + atribuição
}
console.log(mensagem);
=> undefined

Return is not something like a reference error, but undefined , the default value of every variable declared in JavaScript.

This is by hoisting , a mechanism that declares all variables even before the line of their use is executed. The above code is compiled for:

var mensagem;        // declaração
if(false) {
  mensagem = "Olá!"; // atribuição
}
console.log(mensagem);
=> undefined

For me, this is actually a performance and encapsulation problem for scopes. Am I right? Is there any hoisting utility in JavaScript? Why was this behavior so?

In ES6, with let and const , hoisting in the scope of functions has been eliminated and the above example causes ReferenceError .

    
asked by anonymous 26.02.2018 / 01:14

1 answer

3

Be careful, this is not true. Not all variables in a function are created independently of JS scope. See:

function x() {
  y = 1;
  var z = 2;
}

x();

console.log(y); // logs "1" 
console.log(z); // Throws a ReferenceError: z is not defined outside x

When you declare a variable without var , the compiler declares the global variable, and if it is declared with var , it creates within the scope.

However, in your code, you declared the variable with var and it created the variable in global-scope, why? Your code works because in javascript var exists only in two types of scopes: global-scope and function-scope , which are scopes created by functions. The block-scopes , which are created by { ... } , were created from ES6 with the creation of let and const types. So, since you're using var, it's as if all of your code is in the same scope, so it does not make a mistake. Now, try:

function teste() {
  var mensagem = "Olá!"; // declaração + atribuição
}
console.log(mensagem); // ReferenceError: mensagem is not defined

So, in fact, before ES6, when there was only var , you could only create variables in global scope and function scope . Javascript did not have block scopes .

And in ES6 hoisting was not deleted, but created the block scopes , which is where the let and const variables are created. That is why using let or const in your example gives error:

if(false) {
  let mensagem = "Olá!"; // declaração + atribuição
}
console.log(mensagem); // ReferenceError: mensagem is not defined

The hoisting exists because the javascript interpreter executes its code in two steps: in the first compiler-phase all variables and functions are allocated in memory (it's as if we were passing the variables and functions up), and in the second, execution-phase , your code starts running line by line.

What we, devs, can take away from this is to be able to use the variables and functions before they are declared:

i = 10;
var i;

and with methods:

issoEhHoisting();
function issoEhHoisting(){
    console.log("aqui esta minha declaração");
}

The two blocks above only work because of hoisting .

    
26.02.2018 / 06:11