Tôi đã từng biết điều này có nghĩa là gì, nhưng giờ tôi đang vật lộn ...
Đây có phải là về cơ bản nói document.onload
?
(function () {
})();
Tôi đã từng biết điều này có nghĩa là gì, nhưng giờ tôi đang vật lộn ...
Đây có phải là về cơ bản nói document.onload
?
(function () {
})();
Câu trả lời:
Đó là một biểu thức chức năng được gọi ngay lập tức , hoặc IIFE viết tắt là . Nó thực thi ngay sau khi nó được tạo.
Nó không có gì để làm với bất kỳ xử lý sự kiện cho bất kỳ sự kiện (chẳng hạn như document.onload
).
Hãy xem xét phần trong cặp dấu ngoặc đơn đầu tiên: .... đó là biểu thức hàm thông thường. Sau đó nhìn vào cặp cuối cùng , điều này thường được thêm vào một biểu thức để gọi hàm; trong trường hợp này, biểu hiện trước của chúng tôi.(function(){})();
(function(){})();
Mẫu này thường được sử dụng khi cố gắng tránh gây ô nhiễm không gian tên toàn cầu, bởi vì tất cả các biến được sử dụng bên trong IIFE (giống như trong bất kỳ chức năng bình thường nào khác ) không thể nhìn thấy ngoài phạm vi của nó.
Đây là lý do tại sao, có thể, bạn đã nhầm lẫn công trình này với một trình xử lý sự kiện window.onload
, bởi vì nó thường được sử dụng như sau:
(function(){
// all your code here
var foo = function() {};
window.onload = foo;
// ...
})();
// foo is unreachable here (it’s undefined)
Sửa chữa được đề xuất bởi Guffa :
Hàm được thực thi ngay sau khi được tạo, không phải sau khi được phân tích cú pháp. Toàn bộ khối tập lệnh được phân tích cú pháp trước khi bất kỳ mã nào trong đó được thực thi. Ngoài ra, mã phân tích không tự động có nghĩa là nó được thực thi, ví dụ như IIFE nằm trong một hàm thì nó sẽ không được thực thi cho đến khi hàm được gọi.
Cập nhật Vì đây là một chủ đề khá phổ biến, điều đáng nói là IIFE cũng có thể được viết bằng chức năng mũi tên của ES6 (như Gajus đã chỉ ra trong một bình luận ):
((foo) => {
// do something with foo here foo
})('foo value')
function(){ var foo = '5'; }
Nó chỉ là một chức năng ẩn danh được thực thi ngay sau khi nó được tạo.
Giống như bạn đã gán nó cho một biến và sử dụng nó ngay sau đó, chỉ khi không có biến:
var f = function () {
};
f();
Trong jQuery có một cấu trúc tương tự mà bạn có thể nghĩ đến:
$(function(){
});
Đó là hình thức ràng buộc ngắn của ready
sự kiện:
$(document).ready(function(){
});
Nhưng hai cấu trúc trên không phải là IIFE s.
Một biểu thức hàm được gọi ngay lập tức (IIFE) ngay lập tức gọi một hàm. Điều này chỉ có nghĩa là hàm được thực thi ngay sau khi hoàn thành định nghĩa.
Ba từ phổ biến hơn:
// Crockford's preference - parens on the inside
(function() {
console.log('Welcome to the Internet. Please follow me.');
}());
//The OPs example, parentheses on the outside
(function() {
console.log('Welcome to the Internet. Please follow me.');
})();
//Using the exclamation mark operator
//https://stackoverflow.com/a/5654929/1175496
!function() {
console.log('Welcome to the Internet. Please follow me.');
}();
Nếu không có yêu cầu đặc biệt cho giá trị trả về của nó, thì chúng ta có thể viết:
!function(){}(); // => true
~function(){}(); // => -1
+function(){}(); // => NaN
-function(){}(); // => NaN
Ngoài ra, nó có thể là:
~(function(){})();
void function(){}();
true && function(){ /* code */ }();
15.0, function(){ /* code */ }();
Bạn thậm chí có thể viết:
new function(){ /* code */ }
31.new function(){ /* code */ }() //If no parameters, the last () is not required
31.new
cú cuối cùng 'là cú pháp không hợp lệ
;(function(){}());
1 - 1
và bạn có thể dễ dàng làm như vậy true - function(){}
. Đó chỉ là một điều (một toán tử trừ infix) nhưng với các toán hạng khác nhau, thậm chí vô nghĩa.
Nó khai báo một hàm ẩn danh, sau đó gọi nó:
(function (local_arg) {
// anonymous function
console.log(local_arg);
})(arg);
Đó là nói thực thi ngay lập tức.
vì vậy nếu tôi làm:
var val = (function(){
var a = 0; // in the scope of this function
return function(x){
a += x;
return a;
};
})();
alert(val(10)); //10
alert(val(11)); //21
Fiddle: http://jsfiddle.net/manoder/LqvpQ/
var val = (function(){
return 13 + 5;
})();
alert(val); //18
Cấu trúc đó được gọi là Biểu thức hàm được gọi ngay lập tức (IIFE) có nghĩa là nó được thực thi ngay lập tức. Hãy nghĩ về nó như là một chức năng được gọi tự động khi trình thông dịch đạt đến chức năng đó.
Trường hợp sử dụng phổ biến nhất:
Một trong những trường hợp sử dụng phổ biến nhất của nó là giới hạn phạm vi của một biến được thực hiện thông qua var
. Các biến được tạo thông quavar
có phạm vi giới hạn trong một hàm nên cấu trúc này (là trình bao bọc hàm xung quanh mã nhất định) sẽ đảm bảo rằng phạm vi biến của bạn không bị rò rỉ ra khỏi hàm đó.
Trong ví dụ sau, count
sẽ không có sẵn bên ngoài hàm được gọi ngay lập tức tức là phạm vi count
sẽ không bị rò rỉ ra khỏi hàm. Bạn sẽ nhận được một ReferenceError
, nếu bạn cố gắng truy cập nó bên ngoài chức năng được gọi ngay lập tức.
(function () {
var count = 10;
})();
console.log(count); // Reference Error: count is not defined
Thay thế ES6 (Khuyến nghị)
Trong ES6, bây giờ chúng ta có thể có các biến được tạo thông qua let
và const
. Cả hai đều có phạm vi khối (không giống như var
phạm vi chức năng).
Do đó, thay vì sử dụng cấu trúc IIFE phức tạp đó cho trường hợp sử dụng mà tôi đã đề cập ở trên, giờ đây bạn có thể viết mã đơn giản hơn nhiều để đảm bảo rằng phạm vi của một biến không bị rò rỉ ra khỏi khối mong muốn của bạn.
{
let count = 10;
}
console.log(count); // ReferenceError: count is not defined
Trong ví dụ này, chúng tôi đã sử dụng let
để xác định count
biến làm cho count
giới hạn trong khối mã, chúng tôi đã tạo bằng dấu ngoặc nhọn {...}
.
Tôi gọi nó là một nhà tù xoăn xoăn.
(function () {
})();
Điều này được gọi là IIFE (Biểu thức chức năng được gọi ngay lập tức). Một trong những mẫu thiết kế JavaScript nổi tiếng, đó là trái tim và linh hồn của mẫu Mô-đun hiện đại. Như tên cho thấy nó thực thi ngay sau khi nó được tạo. Mẫu này tạo ra một phạm vi thực thi riêng biệt hoặc riêng tư.
JavaScript trước ECMAScript 6 đã sử dụng phạm vi từ vựng, vì vậy IIFE đã được sử dụng để mô phỏng phạm vi khối. (Với phạm vi khối ECMAScript 6 là có thể với việc giới thiệu các từ khóa let
và const
.)
Tham khảo cho vấn đề với phạm vi từ vựng
Mô phỏng phạm vi khối với IIFE
Lợi ích của việc sử dụng hiệu suất IIFE là khả năng để vượt qua thường được sử dụng đối tượng toàn cầu như window
, document
vv như một cuộc tranh cãi bằng cách giảm tra cứu phạm vi. (Hãy nhớ JavaScript tìm các thuộc tính trong phạm vi cục bộ và tăng chuỗi cho đến phạm vi toàn cầu). Vì vậy, truy cập các đối tượng toàn cầu trong phạm vi địa phương làm giảm thời gian tra cứu như dưới đây.
(function (globalObj) {
//Access the globalObj
})(window);
Không, cấu trúc này chỉ tạo ra một phạm vi để đặt tên. Nếu bạn phá vỡ nó trong các phần bạn có thể thấy rằng bạn có một bên ngoài
(...)();
Đó là một lời gọi hàm. Trong ngoặc đơn bạn có:
function() {}
Đó là một chức năng ẩn danh. Mọi thứ được khai báo với var bên trong cấu trúc sẽ chỉ hiển thị bên trong cùng một cấu trúc và sẽ không gây ô nhiễm không gian tên toàn cục.
Đây là một biểu thức chức năng được gọi ngay lập tức trong Javascript:
Để hiểu IIFE trong JS, hãy chia nhỏ nó:
a = 10 output = 10 (1+3) output = 4
// Function Expression var greet = function(name){ return 'Namaste' + ' ' + name; } greet('Santosh');
Cách biểu thức chức năng hoạt động:
- Khi công cụ JS chạy lần đầu tiên (Bối cảnh thực thi - Tạo pha), chức năng này (ở phía bên phải của = ở trên) không được thực thi hoặc lưu trữ trong bộ nhớ. Biến 'lời chào' được gán bởi giá trị 'không xác định' bởi công cụ JS.
- Trong khi thực hiện (Bối cảnh thực thi - Giai đoạn thực thi), đối tượng funtion được tạo khi đang bay ( chưa được thực thi ), được gán cho biến 'hello' và nó có thể được gọi bằng 'hello (' somename ')'.
3. Biểu hiện Funtion ngay lập tức được viện dẫn:
Thí dụ:
// IIFE
var greeting = function(name) {
return 'Namaste' + ' ' + name;
}('Santosh')
console.log(greeting) // Namaste Santosh.
Cách IIFE hoạt động :
- Lưu ý '()' ngay sau khi khai báo hàm. Mọi đối tượng funtion đều có thuộc tính 'CODE' được gắn vào nó có thể gọi được. Và chúng ta có thể gọi nó (hoặc gọi nó) bằng cách sử dụng dấu ngoặc '()'.
- Vì vậy, ở đây, trong quá trình thực thi (Bối cảnh thực thi - Giai đoạn thực thi), đối tượng hàm được tạo và được thực thi cùng lúc
- Vì vậy, bây giờ, biến chào, thay vì có đối tượng funtion, có giá trị trả về (một chuỗi)
Usecase điển hình của IIFE trong JS:
Mẫu IIFE sau đây được sử dụng khá phổ biến.
// IIFE
// Spelling of Function was not correct , result into error
(function (name) {
var greeting = 'Namaste';
console.log(greeting + ' ' + name);
})('Santosh');
Vì vậy, chức năng này được tạo và thực hiện cùng một lúc (IIFE).
Usecase quan trọng cho IIFE:
IIFE giữ mã của chúng tôi an toàn.
- IIFE, là một hàm, có bối cảnh thực thi riêng, có nghĩa là tất cả các biến được tạo bên trong nó là cục bộ của hàm này và không được chia sẻ với bối cảnh thực thi toàn cục.
Giả sử tôi có một tệp JS khác (test1.js) được sử dụng trong applicaiton của tôi cùng với iife.js (xem bên dưới).
// test1.js
var greeting = 'Hello';
// iife.js
// Spelling of Function was not correct , result into error
(function (name) {
var greeting = 'Namaste';
console.log(greeting + ' ' + name);
})('Santosh');
console.log(greeting) // No collision happens here. It prints 'Hello'.
Vì vậy, IIFE giúp chúng tôi viết mã an toàn khi chúng tôi không va chạm với các đối tượng toàn cầu.
Đó là một chức năng ẩn danh tự gọi .
Kiểm tra giải thích của W3Schools về chức năng tự gọi .
Các biểu thức chức năng có thể được thực hiện "tự gọi".
Một biểu thức tự gọi được gọi tự động (bắt đầu) mà không được gọi.
Các biểu thức hàm sẽ thực thi tự động nếu biểu thức được theo sau bởi ().
Bạn không thể tự gọi một khai báo hàm.
(function named(){console.log("Hello");}());
<- chức năng tự thực hiện có tên
Đây là chức năng ẩn danh tự gọi. Nó được thực thi trong khi nó được xác định. Có nghĩa là chức năng này được định nghĩa và gọi chính nó ngay sau định nghĩa.
Và giải thích của cú pháp là: Hàm trong ()
ngoặc đơn đầu tiên là hàm không có tên và bằng ();
dấu ngoặc đơn tiếp theo, bạn có thể hiểu rằng nó được gọi tại thời điểm được định nghĩa. Và bạn có thể vượt qua bất kỳ đối số nào trong ()
ngoặc đơn thứ hai này sẽ được lấy trong hàm nằm trong ngoặc đơn đầu tiên. Xem ví dụ này:
(function(obj){
// Do something with this obj
})(object);
Ở đây, 'đối tượng' bạn đang vượt qua sẽ có thể truy cập được trong hàm bằng 'obj', khi bạn đang lấy nó trong chữ ký hàm.
Bắt đầu ở đây:
var b = 'bee';
console.log(b); // global
Đặt nó trong một chức năng và nó không còn toàn cầu - mục tiêu chính của bạn.
function a() {
var b = 'bee';
console.log(b);
}
a();
console.log(b); // ReferenceError: b is not defined -- *as desired*
Gọi chức năng ngay lập tức - rất tiếc:
function a() {
var b = 'bee';
console.log(b);
}(); // SyntaxError: Expected () to start arrow function, but got ';' instead of '=>'
Sử dụng dấu ngoặc đơn để tránh lỗi cú pháp:
(function a() {
var b = 'bee';
console.log(b);
})(); // OK now
Bạn có thể bỏ tên hàm:
(function () { // no name required
var b = 'bee';
console.log(b);
})();
Nó không cần phải phức tạp hơn thế.
Uncaught SyntaxError: Unexpected token )
chứ không phải bất kỳ đề cập đến chức năng mũi tên. Bạn có thể chia sẻ một câu đố với nó ném lỗi chức năng mũi tên?
Chức năng ẩn danh tự thực hiện. Nó được thực hiện ngay khi nó được tạo ra.
Một ví dụ ngắn và giả trong đó hữu ích là:
function prepareList(el){
var list = (function(){
var l = [];
for(var i = 0; i < 9; i++){
l.push(i);
}
return l;
})();
return function (el){
for(var i = 0, l = list.length; i < l; i++){
if(list[i] == el) return list[i];
}
return null;
};
}
var search = prepareList();
search(2);
search(3);
Vì vậy, thay vì tạo danh sách mỗi lần, bạn chỉ tạo một danh sách (ít chi phí hơn).
Các chức năng tự thực thi thường được sử dụng để đóng gói bối cảnh và tránh các thông đồng tên. Bất kỳ biến nào bạn xác định bên trong (function () {..}) () không phải là toàn cục.
Mật mã
var same_name = 1;
var myVar = (function() {
var same_name = 2;
console.log(same_name);
})();
console.log(same_name);
tạo đầu ra này:
2
1
Bằng cách sử dụng cú pháp này, bạn tránh va chạm với các biến toàn cục được khai báo ở nơi khác trong mã JavaScript của bạn.
var same_name = 1; var myVar = function() { var same_name = 2; console.log(same_name); }; myVar(); console.log(same_name);
Sẽ có kết quả tương tự.
Nó được gọi là IIFE - Biểu thức hàm được gọi ngay lập tức. Dưới đây là một ví dụ để hiển thị cú pháp và cách sử dụng. Nó được sử dụng để phạm vi sử dụng các biến chỉ cho đến hàm và không vượt quá.
(function () {
function Question(q,a,c) {
this.q = q;
this.a = a;
this.c = c;
}
Question.prototype.displayQuestion = function() {
console.log(this.q);
for (var i = 0; i < this.a.length; i++) {
console.log(i+": "+this.a[i]);
}
}
Question.prototype.checkAnswer = function(ans) {
if (ans===this.c) {
console.log("correct");
} else {
console.log("incorrect");
}
}
var q1 = new Question('Is Javascript the coolest?', ['yes', 'no'], 0);
var q2 = new Question('Is python better than Javascript?', ['yes', 'no', 'both are same'], 2);
var q3 = new Question('Is Javascript the worst?', ['yes', 'no'], 1);
var questions = [q1, q2, q3];
var n = Math.floor(Math.random() * questions.length)
var answer = parseInt(prompt(questions[n].displayQuestion()));
questions[n].checkAnswer(answer);
})();
IIFE (Biểu thức hàm được gọi ngay lập tức) là một hàm thực thi ngay khi tập lệnh tải và biến mất.
Hãy xem xét hàm bên dưới được viết trong một tệp có tên iife.js
(function(){
console.log("Hello Stackoverflow!");
})();
Mã này ở trên sẽ thực thi ngay khi bạn tải iife.js và sẽ in ' Xin chào Stackoverflow! 'trên bảng điều khiển của công cụ dành cho nhà phát triển.
Để được giải thích chi tiết, hãy xem Biểu thức chức năng được gọi ngay lập tức (IIFE)
Một trường hợp sử dụng nữa là ghi nhớ trong đó một đối tượng bộ đệm không phải là toàn cục:
var calculate = (function() {
var cache = {};
return function(a) {
if (cache[a]) {
return cache[a];
} else {
// Calculate heavy operation
cache[a] = heavyOperation(a);
return cache[a];
}
}
})();
Một biểu thức hàm được gọi ngay lập tức (IIFE) là một hàm được thực thi ngay khi nó được tạo. Nó không có kết nối với bất kỳ sự kiện hoặc thực thi không đồng bộ. Bạn có thể định nghĩa IIFE như hình dưới đây:
(function() {
// all your code here
// ...
})();
Cặp dấu ngoặc đơn đầu tiên () {...} chuyển đổi mã bên trong dấu ngoặc đơn thành một biểu thức. Cặp dấu ngoặc đơn thứ hai gọi hàm kết quả từ biểu thức.
An IIFE
cũng có thể được mô tả như là một hàm ẩn danh tự gọi. Cách sử dụng phổ biến nhất của nó là giới hạn phạm vi của một biến được thực hiện thông qua var hoặc đóng gói bối cảnh để tránh xung đột tên.
Lý do các hàm ẩn danh tự kích hoạt được sử dụng là chúng không bao giờ được gọi bởi mã khác vì chúng "thiết lập" mã mà IS có nghĩa là được gọi (cùng với việc đưa ra phạm vi cho các hàm và biến).
Nói cách khác, chúng giống như các chương trình "tạo lớp", ở đầu chương trình. Sau khi chúng được khởi tạo (tự động), các hàm duy nhất có sẵn là các hàm được trả về bởi hàm ẩn danh. Tuy nhiên, tất cả các hàm khác ' Các hàm 'ẩn' vẫn còn đó, cùng với bất kỳ trạng thái nào (các biến được đặt trong quá trình tạo phạm vi).
Rất tuyệt.
Các mã sau đây:
(function () {
})();
được gọi là biểu thức hàm được gọi ngay lập tức (IIFE).
Nó được gọi là biểu thức hàm vì ( yourcode )
toán tử trong Javascript buộc nó thành biểu thức. Sự khác biệt giữa biểu thức hàm và khai báo hàm là như sau:
// declaration:
function declaredFunction () {}
// expressions:
// storing function into variable
const expressedFunction = function () {}
// Using () operator, which transforms the function into an expression
(function () {})
Một biểu thức chỉ đơn giản là một bó mã có thể được ước tính thành một giá trị duy nhất . Trong trường hợp các biểu thức trong ví dụ trên, giá trị này là một đối tượng hàm duy nhất .
Sau khi chúng ta có một biểu thức ước lượng cho một đối tượng hàm, sau đó chúng ta có thể gọi ngay đối tượng hàm với ()
toán tử. Ví dụ:
(function() {
const foo = 10; // all variables inside here are scoped to the function block
console.log(foo);
})();
console.log(foo); // referenceError foo is scoped to the IIFE
Khi chúng tôi đang xử lý một cơ sở mã lớn và / hoặc khi chúng tôi đang nhập các thư viện khác nhau, cơ hội đặt tên xung đột sẽ tăng lên. Khi chúng tôi viết một số phần nhất định của mã có liên quan (và do đó đang sử dụng cùng một biến) trong IIFE, tất cả các biến và tên hàm được đặt trong phạm vi dấu ngoặc của IIFE . Điều này làm giảm cơ hội đặt tên xung đột và cho phép bạn đặt tên cho chúng bất cẩn hơn (ví dụ: bạn không phải đặt tiền tố cho chúng).
Hàm này được gọi là hàm tự gọi. Hàm tự gọi (còn gọi là tự thực thi) là một hàm không tên (ẩn danh) được gọi (Gọi) ngay sau định nghĩa của nó.Đọc thêm tại đây
Những chức năng này làm là khi hàm được xác định, Hàm được gọi ngay lập tức, giúp tiết kiệm thời gian và các dòng mã bổ sung (so với việc gọi nó trên một dòng riêng biệt).
Đây là một ví dụ:
(function() {
var x = 5 + 4;
console.log(x);
})();
Đây là một lời giải thích sâu hơn về lý do tại sao bạn sẽ sử dụng điều này:
"Lý do chính để sử dụng IIFE là để có được quyền riêng tư dữ liệu. Bởi vì var var của JavaScript biến các hàm chứa của chúng, bất kỳ biến nào được khai báo trong IIFE đều không thể được truy cập bởi thế giới bên ngoài."
Nó là một biểu thức hàm, nó là viết tắt của Biểu thức hàm được gọi ngay lập tức (IIFE). IIFE đơn giản là một chức năng được thực thi ngay sau khi nó được tạo. Vì vậy, do chức năng phải đợi cho đến khi nó được gọi để thực thi, IIFE được thực thi ngay lập tức. Hãy xây dựng IIFE bằng ví dụ. Giả sử chúng ta có một hàm add có hai số nguyên là arg và trả về tổng cho phép biến hàm add thành IIFE,
Bước 1: Xác định chức năng
function add (a, b){
return a+b;
}
add(5,5);
Bước2: Gọi hàm bằng cách gói toàn bộ khai báo dấu chấm vào dấu ngoặc đơn
(function add (a, b){
return a+b;
})
//add(5,5);
Bước 3: Để gọi hàm ngay lập tức, chỉ cần xóa văn bản 'thêm' khỏi cuộc gọi.
(function add (a, b){
return a+b;
})(5,5);
Lý do chính để sử dụng IFFE là để duy trì phạm vi riêng tư trong chức năng của bạn. Bên trong mã javascript của bạn, bạn muốn đảm bảo rằng, bạn không ghi đè bất kỳ biến toàn cục nào. Đôi khi bạn có thể vô tình xác định một biến ghi đè lên một biến toàn cục. Hãy thử làm ví dụ. giả sử chúng ta có một tệp html có tên iffe.html và các mã bên trong thẻ body là-
<body>
<div id = 'demo'></div>
<script>
document.getElementById("demo").innerHTML = "Hello JavaScript!";
</script>
</body>
Chà, đoạn mã trên sẽ thực thi với bất kỳ câu hỏi nào, bây giờ giả sử bạn tuyên bố một biến có tên là tài liệu vô tình hoặc cố ý.
<body>
<div id = 'demo'></div>
<script>
document.getElementById("demo").innerHTML = "Hello JavaScript!";
const document = "hi there";
console.log(document);
</script>
</body>
bạn sẽ kết thúc bằng SyntaxError : khai báo lại tài liệu thuộc tính toàn cầu không thể cấu hình.
Nhưng nếu mong muốn của bạn là từ chối một tài liệu tên biến, bạn có thể thực hiện bằng cách sử dụng IFFE.
<body>
<div id = 'demo'></div>
<script>
(function(){
const document = "hi there";
this.document.getElementById("demo").innerHTML = "Hello JavaScript!";
console.log(document);
})();
document.getElementById("demo").innerHTML = "Hello JavaScript!";
</script>
</body>
Đầu ra:
Hãy thử một ví dụ khác, giả sử chúng ta có một đối tượng máy tính như dưới đây-
<body>
<script>
var calculator = {
add:function(a,b){
return a+b;
},
mul:function(a,b){
return a*b;
}
}
console.log(calculator.add(5,10));
</script>
</body>
Chà, nó hoạt động như một bùa mê, điều gì sẽ xảy ra nếu chúng ta vô tình gán lại giá trị của đối tượng máy tính.
<body>
<script>
var calculator = {
add:function(a,b){
return a+b;
},
mul:function(a,b){
return a*b;
}
}
console.log(calculator.add(5,10));
calculator = "scientific calculator";
console.log(calculator.mul(5,5));
</script>
</body>
vâng, bạn sẽ kết thúc với TypeError: Calculator.mul không phải là một hàm iffe.html
Nhưng với sự giúp đỡ của IFFE, chúng ta có thể tạo một phạm vi riêng tư nơi chúng ta có thể tạo một máy tính tên biến khác và sử dụng nó;
<body>
<script>
var calculator = {
add:function(a,b){
return a+b;
},
mul:function(a,b){
return a*b;
}
}
var cal = (function(){
var calculator = {
sub:function(a,b){
return a-b;
},
div:function(a,b){
return a/b;
}
}
console.log(this.calculator.mul(5,10));
console.log(calculator.sub(10,5));
return calculator;
})();
console.log(calculator.add(5,10));
console.log(cal.div(10,5));
</script>
</body>
Tôi nghĩ rằng 2 bộ dấu ngoặc làm cho nó hơi khó hiểu nhưng tôi đã thấy một cách sử dụng khác trong ví dụ về Google, họ đã sử dụng một cái gì đó tương tự, tôi hy vọng điều này sẽ giúp bạn hiểu rõ hơn:
var app = window.app || (window.app = {});
console.log(app);
console.log(window.app);
Vì vậy, nếu windows.app
không được xác định, thì window.app = {}
ngay lập tức được thực thi, do đó window.app
được gán {}
trong quá trình đánh giá điều kiện, do đó, kết quả là cả hai app
và window.app
bây giờ trở thành {}
, vì vậy đầu ra của giao diện điều khiển là:
Object {}
Object {}
Thông thường, mã JavaScript có phạm vi toàn cầu trong ứng dụng. Khi chúng ta khai báo biến toàn cục trong đó, có một cơ hội sử dụng cùng một biến trùng lặp trong một số lĩnh vực phát triển khác cho một số mục đích khác. Do sự trùng lặp này có thể xảy ra một số lỗi. Vì vậy, chúng ta có thể tránh các biến toàn cục này bằng cách sử dụng ngay biểu thức hàm, biểu thức này là biểu thức tự thực thi. Khi chúng ta tạo mã của mình trong IIFE này biến toàn cục biểu thức sẽ giống như phạm vi cục bộ và biến cục bộ.
Hai cách chúng ta có thể tạo IIFE
(function () {
"use strict";
var app = angular.module("myModule", []);
}());
HOẶC LÀ
(function () {
"use strict";
var app = angular.module("myModule", []);
})();
Trong đoạn mã trên, ngay bây giờ , ứng dụng var var là một biến cục bộ.