クロージャに関する投稿をいくつか読んでいて、どこでもこれを見ましたが、どのように動作するのか明確な説明はなく、毎回単にそれを使用するように指示されただけでした...:
// Create a new anonymous function, to use as a wrapper
(function(){
// The variable that would, normally, be global
var msg = "Thanks for visiting!";
// Binding a new function to a global object
window.onunload = function(){
// Which uses the 'hidden' variable
alert( msg );
};
// Close off the anonymous function and execute it
})();
新しい匿名関数を作成して実行することがわかりました。その後、この単純なコードが機能するはずです (実際に機能します)。
(function (msg){alert(msg)})('SO');
私の質問は、ここではどんな魔法が起こるのかということです。次のように書いたときにそう思いました。
(function (msg){alert(msg)})
すると、function ""(msg) のような新しい名前のない関数が作成されます...
しかし、なぜこれが機能しないのでしょうか?
(function (msg){alert(msg)});
('SO');
なぜ同じ行にする必要があるのでしょうか?
いくつかの投稿を教えていただくか、説明をお願いできますか?
ベストアンサー1
関数定義の後のセミコロンを削除します。
(function (msg){alert(msg)})
('SO');
上記は動作するはずです。
デモページ:https://jsfiddle.net/e7ooeq6m/
この種のパターンについては、次の投稿で説明しました。
編集:
見てみるとECMA スクリプト仕様関数を定義する方法は 3 つあります。(98 ページ、セクション 13 関数定義)
1. 関数コンストラクタの使用
var sum = new Function('a','b', 'return a + b;');
alert(sum(10, 20)); //alerts 30
2. 関数宣言の使用。
function sum(a, b)
{
return a + b;
}
alert(sum(10, 10)); //Alerts 20;
3. 関数式
var sum = function(a, b) { return a + b; }
alert(sum(5, 5)); // alerts 10
では、宣言と表現の違いは何でしょうか?
ECMA スクリプト仕様より:
関数宣言: 関数識別子 (FormalParameterListopt){ FunctionBody }
関数式: 関数識別子opt ( 形式パラメータリストopt ){ 関数本体 }
ご存知のとおり、関数式では「識別子」はオプションです。識別子を指定しない場合は、無名関数が作成されます。識別子を指定できないという意味ではありません。
これは以下が有効であることを意味します。
var sum = function mySum(a, b) { return a + b; }
重要な点は、'mySum' は mySum 関数本体の内部でのみ使用でき、外部では使用できないことです。次の例を参照してください。
var test1 = function test2() { alert(typeof test2); }
alert(typeof(test2)); //alerts 'undefined', surprise!
test1(); //alerts 'function' because test2 is a function.
これを比較すると
function test1() { alert(typeof test1) };
alert(typeof test1); //alerts 'function'
test1(); //alerts 'function'
この知識を身につけて、コードを分析してみましょう。
次のようなコードの場合、
function(msg) { alert(msg); }
関数式を作成しました。この関数式を括弧で囲むことで実行できます。
(function(msg) { alert(msg); })('SO'); //alerts SO.