Що таке (function () {}) () конструкція в JavaScript?


790

Раніше я знав, що це означає, але я зараз борюся ...

Це в основному говорить document.onload?

(function () {

})();

20
btw, хоча ви побачите людей, які називають цю функцію «самозванкою», це явно не вірно. Термін iife має перевагу точності.
AakashM

6
Це дає чудове пояснення цієї конструкції. Тут також походить термін "IIFE". benalman.com/news/2010/11/…
jeremysawesome


2
Для найменування цієї конструкції також подивіться тут . Читайте про мету цієї конструкції та технічне пояснення (також тут ). Для синтаксису погляньте, чому потрібні дужки та куди вони повинні йти .
Бергі

Відповіді:


854

Це вираження функцій негайно , або IIFE . Він виконується відразу після його створення.

Це не має нічого спільного з будь-яким обробником подій для будь-яких подій (наприклад, document.onload).
Розглянемо частину в першій парі в дужках: .... це регулярний вираз функції. Потім подивіться останню пару , це зазвичай додається до виразу для виклику функції; у цьому випадку наш попередній вираз.(function(){})();(function(){})();

Ця закономірність часто використовується, намагаючись уникнути забруднення глобального простору імен, тому що всі змінні, що використовуються всередині IIFE (як і в будь-якій іншій нормальній функції), не видно за її межами.
Ось чому, можливо, ви переплутали цю конструкцію з обробником подій window.onload, оскільки вона часто використовується як така:

(function(){
  // all your code here
  var foo = function() {};
  window.onload = foo;
  // ...
})();
// foo is unreachable here (it’s undefined)

Корекція, запропонована Guffa :

Функція виконується відразу після її створення, а не після її розбору. Весь блок скриптів аналізується до того, як буде виконаний будь-який код у ньому. Крім того, аналіз коду не означає автоматично, що він виконується, якщо, наприклад, IIFE знаходиться у функції, він не буде виконуватися, поки функція не буде викликана.

Оновлення Оскільки це досить популярна тема, варто згадати, що IIFE також можна записати за допомогою функції стрілки ES6 (як Гаджус зазначив у коментарі ):

((foo) => {
 // do something with foo here foo
})('foo value')

@ gion_13 Яка різниця між фазою створення та фазою розбору?
akantoword

1
@jlei, як я бачу, життєвий цикл програми js включає наступні фази: розбір, створення / компіляція, виконання. Хоча реальна реалізація (і іменування :)) може відрізнятися від браузера до браузера, ми можемо визначити ці фази в нашому коді, спостерігаючи за розбіжними помилками, підйомом та помилками виконання часу. Я особисто не знайшов для цього багато ресурсів, оскільки це занадто низький рівень, і програміст не може контролювати це. Ви можете знайти будь - то пояснення в цьому так пост: stackoverflow.com/a/34562772/491075
gion_13

@sam firat усіх, є декларація про варіант та нове ключове слово. Це означає, що у вашому прикладі ви створюєте інстанцію нового об’єкта, визначеного конструктором (анонімний вираз функції), і викликуєте його через новий оператор, а не за допомогою виправлення, як у прикладі IIFE. Впевнені, що ця функція працює як закриття для її вмісту, але це далеко не інший випадок використання.
gion_13

Як це забруднює глобальний простір імен? foo недоступний за межами функції. function(){ var foo = '5'; }
Панкай

1
@Pankaj - Вважається самим собою, це навіть не синтаксично дійсний JS (це вираження функції, але не в контексті вираження, тому трактується як помилка синтаксису).
Квентін

109

Це просто анонімна функція, яка виконується одразу після її створення.

Це так само, як якщо б ви призначили його змінній і використали її відразу після, тільки без змінної:

var f = function () {
};
f();

У jQuery є аналогічна конструкція, про яку ви могли б подумати:

$(function(){
});

Це коротка форма прив'язки readyподії:

$(document).ready(function(){
});

Але два вищезгадані конструкції не є IIFE .


83
Останні два насправді не є IIFE, оскільки вони викликаються, коли DOM буде готовий, а не відразу
svvac

15
@swordofpain: Так, це правильно, вони не є IIFE.
Гуффа

@swordofpain, розглядаючи другий фрагмент; Чи було б якесь значення додавання () до кінця функції, перетворивши його в IIFE?
timebandit

Чи потрібна крапка з комою в кінці?
FrenkyB

@FrenkyB Не потрібно, ні, але рекомендується (крапки з комою часто не потрібні в Javascript, але це хороша практика). Кожен з них - це заяви, які включають анонімні функції, а не декларації функції.
Ледівін

52

Вираз функціонування, який негайно викликається (IIFE), негайно викликає функцію. Це просто означає, що функція виконується відразу після завершення визначення.

Ще три поширені формулювання:

// 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.');
}();

Якщо немає спеціальних вимог до його поверненого значення, тоді ми можемо написати:

!function(){}();  // => true
~function(){}(); // => -1
+function(){}(); // => NaN
-function(){}();  // => NaN

Як варіант, це може бути:

~(function(){})();
void function(){}();
true && function(){ /* code */ }();
15.0, function(){ /* code */ }();

Можна навіть написати:

new function(){ /* code */ }
31.new function(){ /* code */ }() //If no parameters, the last () is not required

4
last one 31.new'- недійсний синтаксис
cat

9
Чому існує так багато способів написати одне і те ж? !! > _ <Мені ця мова не подобається
Awesome_girl

6
а переможець;(function(){}());
Roko C. Buljan

Пояснення уподобань Крокфорда було дуже корисним - пояснює відмінності, які я бачив у дикій природі, наприклад, суть крихітних pubsub jQuery перейшла з однієї версії на іншу (зміни ви можете побачити в кінці файлу), і я не міг ' t з'ясувати, чому.
icc97

1
@Awesome_girl: Це не так, що існує багато способів написати одне і те ж; це те, що JS має систему вільного типу з операторами, які можуть працювати на будь-якому типі значення. Ви можете робити, 1 - 1а так само легко true - function(){}. Це лише одне (оператор віднімання інфіксації), але з різними, навіть безглуздими операндами.

31

Він оголошує анонімну функцію, а потім викликає її:

(function (local_arg) {
   // anonymous function
   console.log(local_arg);
})(arg);

Я здогадуюсь, що "аргументи" - це зовнішні змінні, які посилаються на "arg" для використання в локальному контексті в межах функції?
Далібор

@Dalibor argumentsє особливим ; я здогадуюсь, що відповідач просто перевернув куди імена
кіт

29

Тобто виконайте негайно.

тож якщо я це роблю:

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/maniator/LqvpQ/


Другий приклад:

var val = (function(){
     return 13 + 5;
})();

alert(val); //18

1
Я не розумію, що це доводить самовикликання?
Вихід

1
@Exitos, оскільки він повертає цю функцію. Я наводжу другий приклад.
Naftali aka Neal

дуже легко зрозуміти +1
Adiii

24

Ця конструкція називається виразом негайно викликаних функцій (IIFE), що означає, що вона виконується негайно. Розгляньте це як функцію, яка автоматично викликається, коли інтерпретатор досягне цієї функції.

Найпоширеніші випадки використання:

Один з найпоширеніших випадків його використання - обмеження обсягу змінної, виконаної через var. Змінні, створені за допомогою, varмають обсяг, обмежений функцією, тому ця конструкція (яка є обгорткою функції навколо певного коду) переконається, що ваша змінна область не витікає з цієї функції.

У наступному прикладі countне буде доступним поза функцією, що негайно викликається, тобто сфера дії countне буде витікати з функції. Ви повинні отримати ReferenceError, якщо ви намагаєтесь отримати доступ до нього поза функцією, що негайно викликається.

(function () { 
    var count = 10;
})();
console.log(count);  // Reference Error: count is not defined

ES6 Альтернатива (рекомендується)

В ES6 тепер ми можемо мати змінні, створені через letіconst . Обидва вони мають блок-діапазон (на відміну від varфункціонування).

Тому замість того, щоб використовувати цю складну конструкцію IIFE для згаданого вище випадку використання, тепер ви можете написати набагато простіший код, щоб переконатися, що сфера змінної не витікає з потрібного блоку.

{ 
    let count = 10;
}
console.log(count);  // ReferenceError: count is not defined

У цьому прикладі ми використовували letдля визначення countзмінної, яка countобмежується блоком коду, який ми створили з фігурними дужками {...}.

Я називаю це «Кучерявою тюрмою».


10
Мені подобається Кучеряве в'язниця . Можливо, воно прилипне :)
gion_13

15
(function () {
})();

Це називається IIFE (вираз негайно викликаної функції). Один з найвідоміших моделей дизайну JavaScript, це серце і душа сучасного шаблону модулів. Як випливає з назви, воно виконується відразу після його створення. Ця закономірність створює ізольований або приватний обсяг виконання.

JavaScript до ECMAScript 6 використовував лексичне обстеження, тому IIFE був використаний для імітації блокового масштабування. (За допомогою ECMAScript 6 блокування можливе визначення масштабів із введенням letта constключових слів.) Довідка щодо випуску з лексичним визначенням

Моделюйте масштабування блоку за допомогою IIFE

Виграш в продуктивності використання IIFE є здатність передавати часто використовувані глобальні об'єкти , такі як window, documentі т.д. в якості аргументу за рахунок зменшення пошук області видимості. (Пам'ятайте, що JavaScript шукає властивості в локальному масштабі та піднімає ланцюг до загального масштабу). Таким чином, доступ до глобальних об’єктів у локальному масштабі скорочує час пошуку, як показано нижче.

(function (globalObj) {
//Access the globalObj
})(window);

Дякуємо, що надали суть для розуміння другої дужки в IIFE. Також для уточнення користі глобальної змінної в часі пошуку шляхом визначення їх у визначенні
Arsal

11

Ні, ця конструкція просто створює область для іменування. Якщо розбити його на частини, ви побачите, що у вас є зовнішня

(...)();

Це виклик функції. Всередині дужок у вас є:

function() {}

Це анонімна функція. Все, що оголошено з var всередині конструкції, буде видно лише всередині тієї самої конструкції і не забруднить глобальний простір імен.


11

Це вираження функції негайно викликаного Javascript:

Щоб зрозуміти IIFE в JS, давайте розбийте його:

  1. Вираз : Щось, що повертає значення
    Приклад: Спробуйте дотримуватися в хромованій консолі. Це вирази в JS.
a = 10 
output = 10 
(1+3) 
output = 4
  1. Вираз функції :
    Приклад:
// Function Expression 
var greet = function(name){
   return 'Namaste' + ' ' + name;
}

greet('Santosh');

Як працює вираз функції:
- Коли двигун JS працює вперше (контекст виконання - створення фази), ця функція (з правого боку = вище) не виконується і не зберігається в пам'яті. Двигун JS змінній "привіт" присвоює значення "невизначене".
- Під час виконання (Execution Context - Execute phase) об’єкт функції створюється на льоту ( його ще не виконано ), присвоюється змінній 'привіт' і його можна викликати за допомогою 'вітаю (' якесь ім'я ')'.

3. Виявлення функцій негайно:

Приклад:

// IIFE
var greeting = function(name) {
    return 'Namaste' + ' ' + name;
}('Santosh')

console.log(greeting)  // Namaste Santosh. 

Як працює IIFE :
- Зверніть увагу на (()) відразу після оголошення функції. Кожен об’єкт функціонування має до нього властивість "CODE", яку можна викликати. І ми можемо назвати це (або викликати його), використовуючи брекети '()'.
- Отже, тут під час виконання (Execution Context - Execute Phase) створюється об’єкт функції та виконується його одночасно. Отже, тепер змінна привітання, замість об'єкта функції, має своє повернене значення (рядок)

Типовий випадок використання IIFE в JS:

Наступна схема IIFE досить часто використовується.

// IIFE 
// Spelling of Function was not correct , result into error
(function (name) {
   var greeting = 'Namaste';
   console.log(greeting + ' ' + name);
})('Santosh');
  • ми робимо дві речі тут. а) Загортання нашого вираження функції всередині дужок (). Це означає сказати синтаксичному аналізатору, що все, що міститься всередині (), - це вираз (функція вираз у цьому випадку) і є дійсним кодом.
    б) Ми використовуємо цю функцію одночасно, використовуючи () в кінці її.

Таким чином, ця функція створюється та виконується одночасно (IIFE).

Важливий шафа для IIFE:

IIFE зберігає наш код у безпеці.
- IIFE, будучи функцією, має власний контекст виконання, тобто всі змінні, створені всередині нього, локальні для цієї функції і не поділяються з глобальним контекстом виконання.

Припустимо, у мене є ще один JS-файл (test1.js), який використовується у моєму додатку разом із iife.js (див. Нижче).

// 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'.

Тож IIFE допомагає нам писати безпечний код, коли ми не випадково зіштовхуємось із глобальними об'єктами.


Якщо ми створюємо функції в IIFE, то як ми можемо отримати доступ до них у якомусь іншому файлі js або jsx, тобто в реагуючому компоненті.
кам’яний рок

Хоча ми не використовували IIFE, змінна привітання не зіткнеться з глобальною змінною привітання. То в чому перевага?
Віллі Девід-молодший

6

Це анонімна функція, яка сама викликає .

Ознайомтеся з поясненням W3Schools про функцію самовикликання .

Висловлення функцій можна зробити "самозванком".

Самовикликаючий вираз викликається (запускається) автоматично, без виклику.

Функційні вирази виконуватимуться автоматично, якщо за виразом дотримується ().

Ви не можете самостійно викликати декларацію функції.


3
(function named(){console.log("Hello");}());<-
самовиконання

@bryc навіщо ти називати функцію, якій не потрібно імені.
RicardoGonzales

2
@ RicardoGonzales Recursion Я здогадуюсь
bryc

5

Це анонімна функція самовикликання. Він виконується, поки він визначений. Що означає, що ця функція визначена і викликає себе відразу після визначення.

І пояснення синтаксису: Функція в перших ()дужках - це функція, яка не має імені, і за наступними ();дужками ви можете зрозуміти, що вона викликається в той момент, коли вона визначена. І ви можете передавати будь-який аргумент у цій другій ()дужці, яка буде захоплена у функції, що знаходиться в першій дужці. Дивіться цей приклад:

(function(obj){
    // Do something with this obj
})(object);

Тут 'об’єкт', який ви передаєте, буде доступний у межах функції 'obj', коли ви захоплюєте його в підписі функції.


2
На це запитання вже є прийнята відповідь, і ваша відповідь не додає нічого, що вже не було охоплено прийнятою відповіддю. Отже, абсолютно не було потреби писати цю відповідь.
Аадіт М Шах

3
Мені подобається читати кілька відповідей, іноді фразування того чи іншого має значення.

Я подумав, що це додало, тому що це дозволило мені знати, для чого цей другий набір дужок. Принаймні тут було зрозуміліше, що я бачив.
Johnny

Мої фаворити Обидва кінці зразка IIFE мають параметри, і відображення між ними робиться простим.
Стівен В. Райт

4

Починай тут:

var b = 'bee';
console.log(b);  // global

Покладіть його на функцію, і вона вже не є глобальною - ваша основна мета.

function a() {
  var b = 'bee';
  console.log(b);
}
a();
console.log(b);  // ReferenceError: b is not defined -- *as desired*

Викличте функцію негайно - на жаль:

function a() {
  var b = 'bee';
  console.log(b);
}();             // SyntaxError: Expected () to start arrow function, but got ';' instead of '=>'

Використовуйте дужки, щоб уникнути помилки синтаксису:

(function a() {
  var b = 'bee';
  console.log(b);
})(); // OK now

Ви можете залишити ім'я функції:

(function () {    // no name required
  var b = 'bee';
  console.log(b);
})();

Він не повинен бути складнішим за це.


2
Синтаксична помилка говорить про функції стрілок. Як я розумію, це нова функція js, і вона не існувала кілька років тому, але IIFE. Отже, дужки, ймовірно, використовувались спочатку, щоб уникнути помилки синтаксису, але іншого?
JCarlosR

Не могли б ви відповісти на питання @JCarlos? Оскільки він цілком справедливо зазначає, що IIFE був набагато перед функцією стрілки, це допоможе зрозуміти, для чого потрібне обгортання.
Сценарій47

@ Script47 Я не маю відповіді на питання JCarlos в коментарі. Ви можете сформулювати нове запитання і опублікувати його, і я впевнений, що ви отримаєте кілька хороших відповідей.
Jim Flood

@JCarlos, коли я виконую ту, що видаляє помилку, я фактично отримую, Uncaught SyntaxError: Unexpected token )а не будь-яку згадку про функцію стрілки. Чи можете ви поділитися загадкою з нею, кидаючи помилку функції стрілки?
Сценарій47

2

Самовиконання анонімної функції. Він виконується, як тільки він створений.

Одним із коротких та прикладних прикладів, де це корисно, є:

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);

Тож замість того, щоб створювати список кожного разу, ви створюєте його лише один раз (менше накладних даних).


1
Як написано, ваш пошук відновлює список кожного виклику. Щоб уникнути цього, вам потрібно (1) скласти список та (2) повернути функцію пошуку як закриття, що має доступ до списку, який ви щойно створили. Це ви можете легко зробити за допомогою форми анонімного самовикликання. Дивіться jsfiddle.net/BV4bT .
Джордж

Ви можете пояснити ... менше накладних витрат ... Я розумію цю частину
HIRA THAKUR

2
Накладні засоби означають будь-яку виконану роботу, яка не є необхідною. Популяризація масиву для кожного виклику функції не є необхідним, тому масив у прикладі заповнюється self-exec. анонімна функція лише вперше. Однак, схоже, я помилився у власній відповіді, дивіться посилання в коментарі Джорджа для належного прикладу.
usoban

2

Функції самовиконання зазвичай використовуються для інкапсуляції контексту та уникнення змов імен. Будь-яка змінна, яку ви визначаєте всередині (function () {..}) (), не є глобальною.

Код

var same_name = 1;

var myVar = (function() {
    var same_name = 2;
    console.log(same_name);
})();

console.log(same_name);

виробляє цей вихід:

2
1

Використовуючи цей синтаксис, ви уникаєте зіткнення з глобальними змінними, оголошеними в іншому місці коду JavaScript.


1
Правильно, вихід буде 2, а потім 1, оскільки myVar запускається першим
Далібор

1
Ваше пояснення добре пояснює область функціонування, але не вдається пояснити, чому воно виконується негайно. Призначення його змінної є самовиразним, а також може мати намір, що вона може виконуватися не один раз. var same_name = 1; var myVar = function() { var same_name = 2; console.log(same_name); }; myVar(); console.log(same_name); Був би такий самий результат.
domenicr

2

Він називається IIFE - вираз негайно викликаної функції. Ось приклад, який показує його синтаксис та використання. Він використовується для обмеження використання змінних лише до функції, а не за її межами.

(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);
})();

1

IIFE (Негайно викликаний вираз функції) - це функція, яка виконується, як тільки сценарій завантажується та відходить.

Розглянемо функцію, записану нижче, у файлі під назвою iife.js

(function(){
       console.log("Hello Stackoverflow!");
   })();

Цей код вище буде виконаний, як тільки ви завантажите iife.js, і надрукує " Привіт Stackoverflow!на консолі інструментів розробника.

Для детального пояснення див. Вираз функцій негайно викликаних функцій (IIFE)


1

Ще один випадок використання - це запам'ятовування, коли об'єкт кешу не є глобальним:

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];
    }
  }
})();

0

Вираз виразу функції (IIFE) - це функція, яка виконується, як тільки вона створена. Він не має зв'язку ні з подіями, ні з асинхронним виконанням. Ви можете визначити IIFE, як показано нижче:

(function() {
     // all your code here
     // ...
})();

Перша пара дужок функція () {...} перетворює код усередині дужок у вираз. Друга пара дужок викликає функцію, отриману в результаті виразу.

А IIFEтакож можна охарактеризувати як анонімну функцію, яка викликає самовиклик. Найпоширенішим його використанням є обмеження обсягу змінної, виконаної через var, або для інкапсуляції контексту, щоб уникнути зіткнень імен.


0

Причина використання самозваних анонімних функцій полягає в тому, що їх ніколи не слід викликати іншим кодом, оскільки вони «встановлюють» код, який ІС мав бути викликаний (разом із наданням області функцій та змінних).

Іншими словами, вони схожі на програми, які "складають класи" на початку програми. Після того, як вони створені миттєво (автоматично), єдиними доступними функціями є ті, які повертаються анонімною функцією. Однак усі інші " приховані 'функції все ще є разом із будь-яким станом (змінні, встановлені під час створення області).

Дуже круто.


0

Наступний код:

(function () {

})();

називається виразом функції, що негайно викликається (IIFE).

Його називають виразом функції, оскільки ( yourcode )оператор у Javascript змушує його вираз. Різниця між виразом функції та оголошенням функції полягає в наступному:

// declaration:
function declaredFunction () {}

// expressions:

// storing function into variable
const expressedFunction = function () {}

// Using () operator, which transforms the function into an expression
(function () {})

Вираз - це просто згусток коду, який можна оцінити на одне значення . У разі виразів у наведеному вище прикладі це значення було об'єктом однієї функції .

Після того, як у нас з'явиться вираз, який оцінює об'єкт функції, ми можемо негайно викликати об'єкт функції з ()оператором. Наприклад:

(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

Чому це корисно?

Коли ми маємо справу з великою базою коду та / або при імпорті різних бібліотек, шанс назви конфліктів збільшується. Коли ми пишемо певні частини нашого коду, які пов'язані (і, таким чином, використовуються ті самі змінні) всередині IIFE, всі змінні та назви функцій підпадають під функціональні дужки IIFE . Це зменшує шанси назви конфлікти і дозволяє назвати їх більш необережними (наприклад, не потрібно їх префіксувати).


0

У синтаксисі ES6 (розміщую для себе, коли я постійно розміщую цю сторінку, шукаючи швидкий приклад):

// simple
const simpleNumber = (() => {
  return true ? 1 : 2
})()

// with param
const isPositiveNumber = ((number) => {
  return number > 0 ? true : false
})(4)

0

Ця функція називається функцією самовикликання. Функція самовикликання (її також називають самовиконанням) - це безіменна (анонімна) функція, яка викликається (Викликається) відразу після її визначення. Детальніше читайте тут

Ці функції роблять те, що коли функція визначена, функція негайно викликається, що економить час та зайві рядки коду (порівняно з викликом її окремим рядком).

Ось приклад:

(function() {
    var x = 5 + 4;
    console.log(x);
})();


0

Це більш поглиблене пояснення того, чому ви використовуєте це:

"Основна причина використання IIFE полягає в отриманні конфіденційності даних. Оскільки JavaScript варіює змінні функції, що містять їх функції, будь-які змінні, оголошені в IIFE, не можуть бути доступні зовнішнім світом."

http://adripofjavascript.com/blog/drips/an-introduction-to-iffes-immediate-invoked-function-expressions.html


0

Це вираження функції, воно означає вираз негайно викликаної функції (IIFE). IIFE - це просто функція, яка виконується відразу після її створення. Таким чином, функція, яка повинна чекати, поки вона буде викликана, вона буде виконана негайно. Побудуємо IIFE на прикладі. Припустимо, у нас є функція додавання, яка приймає два цілі числа як аргументи і повертає суму, щоб перетворити функцію додавання у IIFE,

Крок 1: Визначте функцію

function add (a, b){
    return a+b;
}
add(5,5);

Крок 2: Викличте функцію, загорнувши всю декларацію функції у круглі дужки

(function add (a, b){
    return a+b;
})
//add(5,5);

Крок 3. Щоб викликати функцію негайно, просто видаліть текст "додати" з виклику.

(function add (a, b){
    return a+b;
})(5,5);

Основна причина використання IFFE - це збереження приватної сфери в межах вашої функції. Всередині коду javascript ви хочете переконатися, що ви не перекриваєте жодної глобальної змінної. Іноді ви можете випадково визначити змінну, яка перекриває глобальну змінну. Спробуємо на прикладі. припустимо, у нас є файл html під назвою iffe.html, а коди всередині тегу body -

<body>
    <div id = 'demo'></div>
    <script>
        document.getElementById("demo").innerHTML = "Hello JavaScript!";
    </script> 
</body>

Ну, вищезгаданий код буде виконуватись із будь-яким питанням, тепер припустимо, що ви скасуєте змінну з ім'ям документа випадково чи навмисно.

<body>
    <div id = 'demo'></div>
    <script>
        document.getElementById("demo").innerHTML = "Hello JavaScript!";
        const document = "hi there";
        console.log(document);
    </script> 
</body>

ви потрапите в SyntaxError : документа глобальної власності.

Але якщо ваше бажання оголосити документ змінної імені, ви можете зробити це за допомогою 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>

Вихід:

введіть тут опис зображення

Спробуємо на іншому прикладі, припустимо, у нас є об’єкт калькулятора, як

<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>

Добре це працює як принадність, що робити, якщо ми випадково повторно призначимо значення об’єкта калькулятора.

<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>

так, ви закінчите з TypeError: Calculator.mul не є функцією iffe.html

Але за допомогою IFFE ми можемо створити приватну область, де ми можемо створити інший калькулятор імен змінної імені та використовувати її;

<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>

Вихід: введіть тут опис зображення


-1

Я думаю, що два набори дужок робить це дещо заплутаним, але я бачив ще одне використання у прикладі googles, вони використовували щось подібне, сподіваюся, це допоможе вам зрозуміти краще:

var app = window.app || (window.app = {});
console.log(app);
console.log(window.app);

тому, якщо windows.appне визначено, він window.app = {}негайно виконується, тому window.appприсвоюється {}під час оцінки умови, тому результат є обом appі window.appтепер стає {}, тому вихід консолі:

Object {}
Object {}

-1

Зазвичай ми не викликаємо функцію одразу після того, як запишемо її в програму. Вкрай просто кажучи, коли ви викликаєте функцію відразу після її створення, вона називається IIFE - фантазійне ім'я.


-1

Зазвичай код JavaScript має глобальну сферу застосування. Коли ми оголошуємо глобальну змінну в ній, є ймовірність використання тієї ж дублікатної змінної в якійсь іншій області розробки для іншої мети. Через це дублювання може статися якась помилка. Таким чином, ми можемо уникнути цих глобальних змінних, використовуючи негайно виклик функції виразу, цей вираз є самовиконанням виразу. Коли ми робимо наш код всередині цього IIFE виразу. глобальної змінної виразу буде як локальна область дії, так і локальна змінна.

Два способи створити IIFE

(function () {
    "use strict";
    var app = angular.module("myModule", []);
}());

АБО

(function () {
    "use strict";
    var app = angular.module("myModule", []);
})();

У фрагменті коду вище " var app " є локальною змінною.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.