Đóng cửa trong JavaScript
Đóng cửa là gì và khi nào chúng ta thực sự có thể sử dụng nó?
Để hiểu về Closure, chúng ta cần biết về 2 khái niệm đơn giản trong JavaScript: hàm lồng nhau và hàm trả về.
Hàm lồng nhau
Trong JavaScript, chúng ta có thể có các hàm lồng nhau. Hàm bên trong có quyền truy cập vào các biến và tham số của hàm bên ngoài.
Hãy kiểm tra ví dụ sau:
function greetPerson(name) {
const message = 'Hello';
function displayMessage() {
console.log(`${message} ${name}!`);
}
displayMessage();
}
greetPerson('Alex'); // Hello Alex!
Trả lại một chức năng
Bên cạnh việc khai báo và gọi một hàm bên trong bên trong hàm bên ngoài, chúng ta cũng có thể trả về hàm bên trong để nó có thể được gọi từ bên ngoài.
Hãy xem một ví dụ về điều này:
function greetPerson(name) {
const message = 'Hello';
function displayMessage() {
console.log(`${message} ${name}!`);
}
return displayMessage;
}
const displayMessageFunction = greetPerson('Alex');
console.log(typeof(displayMessageFunction)); // function
displayMessageFunction(); // Hello Alex!
Khép kín
Sau khi chúng ta hiểu được 2 khái niệm này thì “định nghĩa” về closure khá đơn giản.
Đóng có nghĩa là hàm bên trong có quyền truy cập vào các biến và tham số của hàm bên ngoài ngay cả sau khi hàm bên ngoài đã trả về.
Hãy xem một ví dụ khác mà chúng ta có thể thấy chính xác cách sử dụng bao đóng:
function counterFunction() {
let counter = 0;
function increaseCounter() {
return counter += 1;
}
return increaseCounter;
}
// counter reffers to the increaseCounter returned by the counterFunction
const counter = counterFunction();
console.log(counter()); // 1
console.log(counter()); // 2
console.log(counter()); // 3
console.log(counter()); // 4
Một hàm bên trong không giữ một bản sao riêng biệt của một biến bên ngoài, nhưng nó tham chiếu đến biến bên ngoài. Nói cách khác, giá trị của countersẽ bị thay đổi nếu bạn thay đổi nó bằng hàm bên trong.
Hàm bên ngoài counterFunctioncũng trả về một tham chiếu đến increaseCounterhàm bên trong, vì vậy khi chúng ta gọi nó, giá trị thực của counterbiến sẽ bị thay đổi. Bằng cách này, chúng ta có thể thấy rằng counterbiến có một giá trị gia tăng mới sau mỗi lần counter()gọi.
Khi nào thì sử dụng Đóng cửa?
Chúng ta có thể sử dụng bao đóng để đạt được tính đóng gói trong JavaScript. Điều này có thể được thực hiện bằng cách ẩn cài đặt chi tiết. Bằng cách này, chúng ta có thể tạo các biến và hàm riêng tư.
Hãy kiểm tra ví dụ sau, nơi chúng tôi muốn đóng gói một số dữ liệu chỉ sử dụng các hàm và đối tượng:
const counter = (function () {
let privateCounter = 0;
function changeBy(val) {
privateCounter += val;
}
function increaseCounter() {
changeBy(1);
}
function decreaseCounter() {
changeBy(-1);
}
function decreaseCounter() {
return privateCounter;
}
return { increaseCounter, decreaseCounter, getCounterValue };
})();
console.log(counter.getCounterValue()); // 0
counter.increaseCounter();
counter.increaseCounter();
console.log(counter.getCounterValue()); // 2
counter.decreaseCounter();
console.log(counter.getCounterValue()); // 1
Chúng ta có thể kiểm soát giá trị của bộ đếm từ bên ngoài, chỉ bằng cách gọi increaseCountervà decreaseCountervà chúng ta có thể lấy giá trị bằng cách gọi getCounterValuehàm, hàm này hoạt động giống như một bộ thu thập.
Bằng cách này, chúng tôi có thể mô phỏng publicvà privatetruy cập các bộ xác định và đạt được sự đóng gói.
Đây là một khái niệm rất mạnh mẽ trong phát triển phần mềm vì nó ngăn chặn các sửa đổi ngoài ý muốn đối với các biến và chức năng nên được giữ riêng tư.
Đó là tất cả!
Cảm ơn bạn đã dành thời gian đọc bài viết này về Closure trong JavaScript. Tôi hy vọng nó đã giúp bạn hiểu rõ hơn về khái niệm quan trọng này và cách nó có thể được sử dụng để đạt được sự đóng gói và tạo các biến và hàm riêng tư!

![Dù sao thì một danh sách được liên kết là gì? [Phần 1]](https://post.nghiatu.com/assets/images/m/max/724/1*Xokk6XOjWyIGCBujkJsCzQ.jpeg)



































