14

Possible Duplicate:
What does (function($) {})(jQuery); mean?

I've seen a lot of jQuery code with the following sort of syntax, but I don't really understand what it means. It shows up in this answer and this answer on a question about code organization. Both talk about namespacing, so I'm guessing that's what it accomplishes.

var foo = (function () {
    var someVar;

    function someFunc() {
        return true;
    }
})();

Is this for namespacing, and how does it work? Sometimes there is a name (the namespace?) in the final set of parentheses, sometimes not. What is the difference between the two?

Peter Mortensen
  • 28,342
  • 21
  • 95
  • 123
keithjgrant
  • 11,328
  • 5
  • 46
  • 83
  • 1
    Also http://stackoverflow.com/questions/4531110/jquerys-function-jquery-syntax/4531124#4531124 – Nikita Rybak Jan 07 '11 at 02:21
  • 1
    This isn't an exact duplicate, as it asks the more general case, not the specific jQuery case - which is an analogue of this. – Orbling Jan 07 '11 at 02:25
  • 1
    @Orbling Yeah, but answers in both questions are not jquery-specific. – Nikita Rybak Jan 07 '11 at 02:27
  • 2
    @Nikita Rybak: True, but I believe we close questions for duplicate questions, not because valid answers can be found under different headings. – Orbling Jan 07 '11 at 02:28
  • 2
    Yes, personally when I find a question that has duplicate answers I post a link to that answer in the Answers section below rather than vote to close. Duplicate answers is not the same as duplicate questions. The question should still be here so that it can be searched. – slebetman Jan 07 '11 at 02:53
  • @slebetman: Quite right, the reason it should stay open as you say is because people search for many cases, regardless of the equality of the answers. If you queried "Breeding Poodles", you would get much the same answers as "Breeding Dogs", one being a subset of the other - does not mean they are exact duplicates and certainly doesn't mean other dog owners wish to search for "poodle breeding" to find out their answer. If anything, the general case (this) has a stronger case. – Orbling Jan 08 '11 at 12:24
  • @Orbling, @slebertman Um, that answer on the dupe *is* about jquery. I don't see the argument here? Besides, even if that question was general javascript and this was jquery-specific, the answers are the same hence they are dupes. See the answers [here](http://meta.stackoverflow.com/questions/38375/what-is-an-exact-duplicate) to better understand the meaning of "exact duplicate". – moinudin Jan 10 '11 at 16:18
  • @Orbling Regarding searching, this question remains in the search results for the exact reason you point out. Then searchers find the link to the duplicate and read those answers. – moinudin Jan 10 '11 at 16:19

2 Answers2

15

The () that wrap the function turns the anonymous function declaration into a function expression that can then be immediately invoked with the () that follows the expression.

In this case, the outer () really isn't necessary since the var foo = would turn it into an expression. Also, the value of foo will be undefined since the function invocation doesn't return anything.

It can be used for creating a new variable scope, since a function is the only way to accomplish that in javascript. (Javascript doesn't have block scope.)

So the someVar variable is not accessible to the outer scope. There may be times when it is desirable to make it accessible in a controlled manner. To do this, you can pass a function out of that scope which references someVar. Then after the function invocation exits, its execution context will remain intact, and someVar will be available in whatever manner the function you passed out provides.

This is called creating a closure.

Let's say you passed a value into the invocation, and assigned it to someVar. You could then return a function out of the invocation to the foo variable. If that function you return references someVar, then you could use that function to get its value.

var foo = (function ( str ) {
    var someVar = str;
/*
    function someFunc() {
        return true;
    }
*/
    return function() {
        alert( someVar );
    };
})( 'somevalue' );

foo(); // alerts 'somevalue'

As you can see, the function now referenced by foo can still access someVar.

Let's say you changed it so that the function returned to foo can accept an argument, which will update the value of myVar.

var foo = (function ( str ) {
    var someVar = str;
/*
    function someFunc() {
        return true;
    }
*/
    return function( n ) {
        if( n ) {
            someVar = n;
        } else {
            alert( someVar );
        }
    };
})( 'somevalue' );

foo(); // alerts 'somevalue'

foo( 'newvalue' ); // give it a new value

foo(); // alerts 'newvalue'

Now you can see, that the function in foo really does access that variable, as it is able to change its value, and reference the new value that it previously set.

user113716
  • 299,514
  • 60
  • 431
  • 433
7

The parentheses wrap around an anonymous function, in order to make it a variable that can be called directly by adding the parameters after it.

(function(param) {
    // do stuff
})(param);

The bit at the end is not a namespace, just a parameter. You have probably seen this used for jQuery as:

(function($) {
    $('.something').addClass('.other');
})(jQuery);

What this does is pass the jQuery object in to the function, making the $ variable the jQuery object in within the scope of the anonymous function. People like to use the shorthand $, but it can lead to conflicts with other libraries. This technique removes the possibility of a conflict by passing the fully qualified jQuery object in and overwriting the $ variable within the scope of that function, so the shortcut can be used.

Orbling
  • 19,537
  • 3
  • 48
  • 64