Why do you need to invoke an anonymous function on the same line?

前端 未结 19 1485
走了就别回头了
走了就别回头了 2020-11-22 00:17

I was reading some posts about closures and saw this everywhere, but there is no clear explanation how it works - everytime I was just told to use it...:

//          


        
相关标签:
19条回答
  • 2020-11-22 00:51
    1. Anonymous functions are functions that are dynamically declared at runtime. They’re called anonymous functions because they aren’t given a name in the same way as normal functions.

      Anonymous functions are declared using the function operator instead of the function declaration. You can use the function operator to create a new function wherever it’s valid to put an expression. For example you could declare a new function as a parameter to a function call or to assign a property of another object.

      Here’s a typical example of a named function:

      function flyToTheMoon() { alert("Zoom! Zoom! Zoom!"); } flyToTheMoon(); Here’s the same example created as an anonymous function:

      var flyToTheMoon = function() { alert("Zoom! Zoom! Zoom!"); } flyToTheMoon();

      For details please read here:

      http://helephant.com/2008/08/23/javascript-anonymous-functions/

    0 讨论(0)
  • 2020-11-22 00:53

    One thing I found confusing is that the "()" are grouping operators.

    Here is your basic declared function.

    Ex. 1:

    var message = 'SO';
    
    function foo(msg) {
        alert(msg);
    }
    
    foo(message);
    

    Functions are objects, and can be grouped. So let's throw parens around the function.

    Ex. 2:

    var message = 'SO';
    
    function foo(msg) {  //declares foo
        alert(msg);
    }
    
    (foo)(message);     // calls foo
    

    Now instead of declaring and right-away calling the same function, we can use basic substitution to declare it as we call it.

    Ex. 3.

    var message = 'SO';
    
    (function foo(msg) {
        alert(msg);
    })(message);          // declares & calls foo
    

    Finally, we don't have a need for that extra foo because we're not using the name to call it! Functions can be anonymous.

    Ex. 4.

    var message = 'SO';
    
    (function (msg) {   // remove unnecessary reference to foo
        alert(msg);
    })(message);
    

    To answer your question, refer back to Example 2. Your first line declares some nameless function and groups it, but does not call it. The second line groups a string. Both do nothing. (Vincent's first example.)

    (function (msg){alert(msg)});  
    ('SO');                       // nothing.
    
    (foo); 
    (msg); //Still nothing.
    

    But

    (foo)
    (msg); //works
    
    0 讨论(0)
  • 2020-11-22 00:54

    Another point of view

    First, you can declare an anonymous function:

    var foo = function(msg){
     alert(msg);
    }
    

    Then you call it:

    foo ('Few');
    

    Because foo = function(msg){alert(msg);} so you can replace foo as:

    function(msg){
     alert(msg);
    } ('Few');
    

    But you should wrap your entire anonymous function inside pair of braces to avoid syntax error of declaring function when parsing. Then we have,

    (function(msg){
     alert(msg);
    }) ('Few');
    

    By this way, It's easy understand for me.

    0 讨论(0)
  • 2020-11-22 00:56

    When you did:

    (function (msg){alert(msg)});
    ('SO');
    

    You ended the function before ('SO') because of the semicolon. If you just write:

    (function (msg){alert(msg)})
    ('SO');
    

    It will work.

    Working example: http://jsfiddle.net/oliverni/dbVjg/

    0 讨论(0)
  • 2020-11-22 00:57

    Drop the semicolon after the function definition.

    (function (msg){alert(msg)})
    ('SO');
    

    Above should work.

    DEMO Page: https://jsfiddle.net/e7ooeq6m/

    I have discussed this kind of pattern in this post:

    jQuery and $ questions

    EDIT:

    If you look at ECMA script specification, there are 3 ways you can define a function. (Page 98, Section 13 Function Definition)

    1. Using Function constructor

    var sum = new Function('a','b', 'return a + b;');
    alert(sum(10, 20)); //alerts 30
    

    2. Using Function declaration.

    function sum(a, b)
    {
        return a + b;
    }
    
    alert(sum(10, 10)); //Alerts 20;
    

    3. Function Expression

    var sum = function(a, b) { return a + b; }
    
    alert(sum(5, 5)); // alerts 10
    

    So you may ask, what's the difference between declaration and expression?

    From ECMA Script specification:

    FunctionDeclaration : function Identifier ( FormalParameterListopt ){ FunctionBody }

    FunctionExpression : function Identifieropt ( FormalParameterListopt ){ FunctionBody }

    If you notice, 'identifier' is optional for function expression. And when you don't give an identifier, you create an anonymous function. It doesn't mean that you can't specify an identifier.

    This means following is valid.

    var sum = function mySum(a, b) { return a + b; }
    

    Important point to note is that you can use 'mySum' only inside the mySum function body, not outside. See following example:

    var test1 = function test2() { alert(typeof test2); }
    
    alert(typeof(test2)); //alerts 'undefined', surprise! 
    
    test1(); //alerts 'function' because test2 is a function.
    

    Live Demo

    Compare this to

     function test1() { alert(typeof test1) };
    
     alert(typeof test1); //alerts 'function'
    
     test1(); //alerts 'function'
    

    Armed with this knowledge, let's try to analyze your code.

    When you have code like,

        function(msg) { alert(msg); }
    

    You created a function expression. And you can execute this function expression by wrapping it inside parenthesis.

        (function(msg) { alert(msg); })('SO'); //alerts SO.
    
    0 讨论(0)
  • 2020-11-22 00:57

    The simple reason why it doesn't work is not because of the ; indicating the end of the anonymous function. It is because without the () on the end of a function call, it is not a function call. That is,

    function help() {return true;}
    

    If you call result = help(); this is a call to a function and will return true.

    If you call result = help; this is not a call. It is an assignment where help is treated like data to be assigned to result.

    What you did was declaring/instantiating an anonymous function by adding the semicolon,

    (function (msg) { /* Code here */ });
    

    and then tried to call it in another statement by using just parentheses... Obviously because the function has no name, but this will not work:

    ('SO');
    

    The interpreter sees the parentheses on the second line as a new instruction/statement, and thus it does not work, even if you did it like this:

    (function (msg){/*code here*/});('SO');
    

    It still doesn't work, but it works when you remove the semicolon because the interpreter ignores white spaces and carriages and sees the complete code as one statement.

    (function (msg){/*code here*/})        // This space is ignored by the interpreter
    ('SO');
    

    Conclusion: a function call is not a function call without the () on the end unless under specific conditions such as being invoked by another function, that is, onload='help' would execute the help function even though the parentheses were not included. I believe setTimeout and setInterval also allow this type of function call too, and I also believe that the interpreter adds the parentheses behind the scenes anyhow which brings us back to "a function call is not a function call without the parentheses".

    0 讨论(0)
提交回复
热议问题