Hoisting

Variable hoisting

Hoisting là một khái niệm trong Javascript mô tả chúng ta có thể sử dụng biến rồi khai báo nó sau.
Giá trị của biến khi khai báo varundefined. Khi khai báo với letconst vẫn được hoist nhưng nó không có giá trị nên sẽ báo lỗi ReferenceError.

Ví dụ viết code thế này:

1
2
console.log(x === undefined); // true, x đã hoisting
var x = 3;

và cách viết code này là giống nhau:

1
2
3
var x;
console.log(x === undefined); // true  
x = 3;

Một ví dụ khi sử dụng cùng tên biến

1
2
3
4
5
6
var myvar = 'Giá trị global';
 
(function() {
  console.log(myvar); // undefined, do sử dụng biến myvar đã hoisting trong hàm này
  var myvar = 'Giá trị local';
})();

Vì tính chất hoisting nên chúng ta nên đặt tất cả các khai báo biến với var ở càng gần đầu của hàm càng tốt. Mã code Javascript như vậy sẽ dễ hiểu, trong sáng hơn.

Hoisting với khi khai báo từ khóa với let hoặc const

Khi hosting với từ khóa let hoặc const sẽ báo lỗi không truy cập được biến khi chưa khởi tạo.

1
2
console.log(x); // ReferenceError, không truy cập được x khi nó chưa được khởi tạo
let x = 3;

Function hoisting

Trong trường hợp hàm, chỉ có các khai báo hàm (Function declaration) được hoisting còn biểu thức hàm (Function expression) thì sẽ nhận giá trị undefined tương tự như khi khai báo biến.

Biểu thức hàm là hàm có dạng var func = function() {...}. Còn khai báo hàm sẽ có dạng function foo() {...}

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
/* Khai báo hàm được hoisting */
foo(); // "foo"
function foo() {
  console.log('foo');
}

/* Biểu thức hàm không được hoisting */
console.log(baz); // undefined
baz(); // TypeError: baz không phải là hàm
var baz = function() {
  console.log('bar');
};