Javascript: почему jQuery делает это: (function () {...}); и как это работает? - PullRequest
1 голос
/ 18 декабря 2009

РЕДАКТИРОВАТЬ: Я ДУМАЛ Исходный код jQuery, на который я смотрел, сделал что-то вроде этого:

(function(){
    var bunchOfVariables = 7;
    jQuery = " ....."; 
    //....
});

Я был неправ в этом. Игнорируйте этот вопрос.


Я не понимаю, что это делает. Может кто-нибудь, пожалуйста, объясните это?

Это самая первая строка в jQuery-1.3.2.js .

Похоже, что он определяет анонимную функцию, а НЕ выполняет ее. Куда идет функция? Как это запустить?

Если я использую такой код в тестовом скрипте, он никогда не будет вызван. С другой стороны, если я следую за ним с пареном «открывать-закрывать», то он вызывается:

// never gets called
(function(){
    say("hello");
});
// gets called
(function(){
    say("buon giorno");
})();

Ответы [ 8 ]

7 голосов
/ 18 декабря 2009

Самая последняя строка источника jQuery:

})();

Скобки означают, что функция вызывается.

4 голосов
/ 18 декабря 2009

Что он на самом деле делает:

(function(){
    var bunchOfVariables = 7;
    jQuery = window.jQuery = window.$ = ...
    //....
})();

Обратите внимание на '()' в конце, который запускает весь этот блок кода. Причина этого заключается в том, чтобы не допустить попадания всех этих связок в глобальную область (читай: окно).

jQuery (и $), однако, становится глобально доступным из-за строки:

jQuery = window.jQuery = window.$ = ...

Помните, что в мире DOM «глобальный» означает «переменная-член окна».

2 голосов
/ 18 декабря 2009
(function() { /* ... */ })();

Этот паттерн обычно называют «самоисполняющейся анонимной функцией». Он определяет новую анонимную функцию (это часть function() { /* ... */ }) и сразу же выполняет ее (то есть () в конце). Дополнительные скобки вокруг объявления функции не являются строго необходимыми, но помогают сделать код более понятным.

Теперь, почему кто-то хотел бы сделать это? Каждая функция в JavaScript имеет свою область видимости. Любые переменные или функции, объявленные в ней, являются локальными для функции и доступны только внутри нее. Допустим, вы пишете плагин jQuery. Может быть, вам нужно много переменных и внутренних методов для вашего плагина. Если вы объявляете все это в самозаполняющейся анонимной функции, вы избегаете загрязнения глобальной области видимости всеми своими внутренними объектами.

2 голосов
/ 18 декабря 2009

Это закрытие, чтобы избежать утечки глобальных символов. Вы определяете функцию и немедленно выполняете ее.

(function(){
  // some code
})();

Обычная версия этого шаблона явно связывает символ '$' с jQuery, если jQuery.noConflict() было вызвано:

(function($){
  // some code here, '$' is bound to jQuery
})(jQuery);
1 голос
/ 18 декабря 2009

jQuery 1.3.2 (текущий выпуск) определяет анонимную функцию в том же духе, но выполняет ее выполнение; Я подозреваю, что вы введены в заблуждение некоторыми ... аномальными отступами, которые они имеют в выпускной копии.

Смысл анонимной функции заключается в предоставлении области видимости. Это называется «модульный шаблон». Вот упрощенный пример

(function() {

    function doSomething() {
        doSomethingElse();
    }

    function doSomethingElse() {
    }

    window.doSomething = doSomething;
})();

(Хотя это не совсем то, как я делал бы шаблон модуля, это похоже на то, как это делает jQuery.)

Теперь есть «публичный» символ (doSomething, который является свойством window), который ссылается на функцию doSomething. Функция doSomethingElse доступна с doSomething, но с нигде больше . Например, это частная сфера.

1 голос
/ 18 декабря 2009

Я думаю, вы можете ошибаться. Первая строка jQuery запускает самозапускающуюся анонимную функцию. Вы уверены, что неправильно сопоставили скобки?

0 голосов
/ 18 декабря 2009

(function() { /* ... */ }) - это не «самозаполняющаяся анонимная функция», () - это не просто «вид кода», они выполняют функцию ...

0 голосов
/ 18 декабря 2009
(function(){
var bunchOfVariables = 7;
jQuery = " ....."; 
//....
});

фактически создает новую анонимную функцию без параметров с некоторой переменной в ней. Но вы только создаете экземпляр, не вызывая саму функцию.

Представьте, что вы хотите сохранить функцию в переменной, которую вы будете делать:

var fn=function(parameter1, parameter2){..}

fn теперь содержит экземпляр анонимной функции, чтобы вызвать его, нужно сделать

fn(arg1, arg2).

Итак, с вашим открытым закрывающим паренем вы просто вызываете функцию, но без аргументов.

...