何の目的で自己実行機能でjavascript?
-
09-09-2019 - |
質問
Javascriptでは、するおそれがある場合は使用していきたいと考えてい:
(function(){
//Bunch of code...
})();
この:
//Bunch of code...
解決
そのすべての変数のスコープについて。自己実行中の関数に宣言された変数は、デフォルトでは、自己実行中の関数内のコードしか利用できます。これは、コードは変数をJavaScriptコードの他のブロックで命名されているかの心配なしに書き込むことができます。
例
(function(){
var foo = 3;
alert(foo);
})();
alert(foo);
これは最初の「3」を警告し、その後、fooが定義されていないため、次の警告にエラーがスローされます。
他のヒント
単純化しました。見ているので、非常に通常、そのほとんど慰めます:
var userName = "Sean";
console.log(name());
function name() {
return userName;
}
しかし。私は、彼らの基本レベルの表現に高度な文字を変換し、私のページには本当に便利なJavaScriptライブラリが含まれている場合は?
待って...何?
私が意味します。 (例えばフランス語やスペイン語の文字など)、その上にアクセントのいくつかの種類の文字であれば、誰かの種類が、私は唯一の英語 '文字をしたいですか?私のプログラムでは、zの?うーん...スペイン語の「n〜」とフランスの「E /」文字が(私はそれらのために2文字ずつを使用しましたが、あなたはおそらくアクセントを表す文字に精神的な飛躍を作ることができる)、それらの文字を翻訳することができます「N」と「E」のベース文字に。
だから、誰かいい人はそこに私はそれを含める...私のサイトに含めることができるという包括的な文字コンバータを書いています。
一つの問題:それはそれで機能が私の関数として「名前」と同じと呼ばれています。
。この衝突と呼ばれるものです。私たちは、同じ名前で同じの範囲の中で宣言した二つの機能を持っています。私たちは、これを回避したいです。
だから我々は何とかスコープに私たちのコードが必要です。
JavaScriptでスコープコードへの唯一の方法は、関数内でそれをラップすることです。
function main() {
// We are now in our own sound-proofed room and the
// character-converter libarary's name() function can exist at the
// same time as ours.
var userName = "Sean";
console.log(name());
function name() {
return userName;
}
}
それが私たちの問題を解決する可能性があります。すべてが今囲まれ、唯一の私たちの開閉括弧内からアクセスすることができます。
私たちは、機能...を見て奇妙である関数を持っていますが、完全に法的ます。
唯一の問題。私たちのコードは動作しません。 私たちのuserName変数は、コンソールにエコーされることはありません!
私たちは、当社の既存のコード・ブロックの後に私たちの関数の呼び出しを追加することで、この問題を解決することができます...
function main() {
// We are now in our own sound-proofed room and the
// character-converter libarary's name() function can exist at the
// same time as ours.
var userName = "Sean";
console.log(name());
function name() {
return userName;
}
}
main();
以前に!
main();
function main() {
// We are now in our own sound-proofed room and the
// character-converter libarary's name() function can exist at the
// same time as ours.
var userName = "Sean";
console.log(name());
function name() {
return userName;
}
}
二次懸念を:名前は「メイン」はまだ使用されていないことのチャンスは何ですか? ...ので、非常に、非常にスリムます。
私たちは、より多くのスコープを必要としています。そして、自動的に私たちのmain()関数を実行するためのいくつかの方法ます。
今、私たちは(、自走、または自己実行何でも)、自動実行機能に来ています。
((){})();
の構文は罪として厄介です。しかし、それは動作します。
するときは、カッコ内の関数定義をラップし、パラメータリストは、(別のセットや括弧を!)それは関数の呼び出しのとして機能します。
だから、いくつかの自己実行する構文で、再び我々のコードを見てみましょます:
(function main() {
var userName = "Sean";
console.log(name());
function name() {
return userName;
}
}
)();
だから、あなたが読んで、ほとんどのチュートリアルでは、あなたが今、用語「匿名の自己実行」または類似した何かを砲撃されます。
専門能力開発の多くの年後、私はを強くのデバッグ目的のためには、の記述名のすべての機能をご促すます。
するとき、何かがうまくいかない(と、それはなります)、あなたがあなたのブラウザでバックトレースをチェックします。 の常にのスタックトレースのエントリが名前を持っていたときにあなたのコードの問題を狭くする方が簡単です!
絶大なロングったらしい、私はそれが役に立てば幸い!
自己呼び出しとしても 自動呼び出し)が機能 を実行した直後、その 定義で設定します。この中核をなすパターン としての多くの その他のパターンのJavaScript 開発。
私の大ファン)で:
- でコードは最小限に
- で執行の分離挙動から発表
- この閉鎖を防止するネーミング紛争
非常に–(うかいに良いの?)
- で定義し、実行する機能です。
- きていること自己実行中の関数戻り値の型関数が値を返すよびパスとしての機能をparamます。
- で封止.
- でもブロックコーピング.
- ええ、すでに同封してすべております。jsファイルの自己実行機能するのを防ぐことが出来ますグローバル名前空間。;)
以上 こちらの.
名前空間。 JavaScriptののスコープは関数レベルです。
私は答えのどれもが暗黙のグローバルを言及していないと信じていないことができます。
(function(){})()
構築物は、= <のhref =「http://yuiblog.com/blog/2006/06/01/global-domination/」RELを参照してください、私には大きな関心事である暗黙のグローバル、保護することはできません。 "nofollowを"> http://yuiblog.com/blog/2006/06/01/global-domination/ の
基本的には、機能ブロックを使用すると、定義されたすべての依存「グローバルVARSは、」あなたのプログラムに限定されているを確認します、それは暗黙のグローバルを定義に対してあなたを保護することはできません。 JSHintするなどは、この動作を防御する方法に関する推奨事項を提供することができます。
より簡潔var App = {}
構文は、保護の同様のレベルを提供し、そして時に「国民ページの機能ブロック内にラップすることができます。 (参照 Ember.js のか、 SproutCore >この構文を使用するライブラリの現実の世界の例)のための
限りprivate
プロパティが行くように、彼らは一種の過大評価ですが、あなたがそれらを実装する必要がある場合は、<のhref = "http://www.crockford.com/javascript/ private.html」のrel = "nofollowを">ダグラス・クロックフォードのいくつかの良いアイデアを持っています。
パラメータや機能を返す「のコードの束が」ありますか?
var a = function(x) { return function() { document.write(x); } }(something);
閉鎖。 something
の値はa
に割り当てられている機能によって使用されます。 something
は(ループ用)、いくつかの様々な値を持つことができ、すべての時間aは、新たな機能を持っています。
っくりとしたすべての回答 何か重要なものが抜けてこちら, んドキドキするでしょう。ある2つの主な要因は、なぜ必要な自己実行機能匿名、又は良い"すぐに呼び出された機能発現(IIFE)":
- より良い名前空間の管理を避ける名前空間の汚染->JSモジュール)
- クロージャ(模擬プライベートクラスの会員として知られているOOP)
最初に説明したようです。のために勉強してください以下の例:
var MyClosureObject = (function (){
var MyName = 'Michael Jackson RIP';
return {
getMyName: function () { return MyName;},
setMyName: function (name) { MyName = name}
}
}());
注意1: または提供する機能 MyClosureObject
, ら の結果を呼び出する機能.注意 ()
になりました。
注意2: いうまたいつの機能でJavascriptの内部機能の取得 アクセスのパラメータと変数 の機能で定義されます。
しましょう実験:
取得できます MyName
を使用 getMyName
での作品:
console.log(MyClosureObject.getMyName());
// Michael Jackson RIP
以下のハープが動作しない:
console.log(MyClosureObject.MyName);
// undefined
ができます設定を別の名前に予期される結果:
MyClosureObject.setMyName('George Michael RIP');
console.log(MyClosureObject.getMyName());
// George Michael RIP
編集: 上記の例では、 MyClosureObject
を設けることなく使用することはでき new
prefix、したがってこの条約すべきではない字にしています。
スコープの分離、多分。関数宣言内の変数は、外側の名前空間を汚染しないようにします。
もちろん、そこに半分JSの実装で、彼らはとにかくされます。
ここで無名関数を呼び出す自己役立つことができる方法の固体の例です。
for( var i = 0; i < 10; i++ ) {
setTimeout(function(){
console.log(i)
})
}
出力:10, 10, 10, 10, 10...
for( var i = 0; i < 10; i++ ) {
(function(num){
setTimeout(function(){
console.log(num)
})
})(i)
}
出力:0, 1, 2, 3, 4...
は一つの違いは、あなたが機能を終了し、他のコード内の他の変数と競合しないとき、彼らは離れて行くので、あなたが関数内で宣言した変数は、ローカルであるということです。
自己呼び出し機能でjavascript:
自己を呼び出す表現が呼び出されます(開始)を自動的にすることなく、呼び出されます。自己を呼び出す表現が呼び出された直後に作成されます。これは基本的には使用を避けるネーミング紛争などの達成に封止.変数は宣言されたオブジェにアクセスできないか、または外にこの機能です。を回避する問題の最小化ファイル名を指定します。分)を使用自己実行されます。
、それが効果的にはるかにC ++やC#のような「クラス」を定義します。
この関数は、ローカル変数を定義し、その内の機能を持つことができます。内部機能(効果インスタンスメソッド)は、ローカル変数(有効インスタンス変数)へのアクセスを有するであろうが、それらは、スクリプトの残りの部分から分離することであろう。
の機能を実行するセルフ変数のスコープを管理するために使用されます。
変数のスコープは、それが定義されているプログラムの領域である。
グローバル変数は、グローバルスコープを有します。それはあなたのJavaScriptコードでどこでも定義されているとも、あなたの機能で、任意の場所にスクリプト内からアクセスすることができます。一方、関数内で宣言された変数は、関数のみの本体内に定義されています。 彼らはローカルスコープを持ち、その関数内でのみアクセスすることができ、ローカル変数です。関数のパラメータは、ローカル変数としてカウントし、関数の本体内でのみ定義されています。
以下に示すように、、あなたはあなたの関数内でグローバル変数の変数にアクセスしても、関数の本体内で、ローカル変数は、同じ名前のグローバル変数よりも優先されることに注意してくださいすることができます。
var globalvar = "globalvar"; // this var can be accessed anywhere within the script
function scope() {
alert(globalvar);
localvar = "localvar" //can only be accessed within the function scope
}
scope();
だから、基本的に自己実行中の関数は、コードは変数をJavaScriptコードの他のブロックで命名されているかの心配なしに書き込むことができます。
このそれは見えます
私は自己実行機能を使用したいときに私は知ってます。
var myObject = {
childObject: new function(){
// bunch of code
},
objVar1: <value>,
objVar2: <value>
}
関数は、私は、このような一般的に使用される変数の設定や数学の方程式を実行するように、掃除機のコードのためchildObjects属性とプロパティを定義するためにいくつかの余分なコードを使用することを可能にします。ああ!またはエラーがチェック。
...のネストされたオブジェクトのインスタンス化の構文に限定されるのではなくobject: {
childObject: {
childObject: {<value>, <value>, <value>}
},
objVar1: <value>,
objVar2: <value>
}
一般的にコーディングあなたは、不思議作り、同じことをたくさんやってのあいまいな方法をたくさん持っている「なぜわざわざ?」しかし、新しい状況が、あなたは、もはや単独の基本/コアプリンシパルに頼ることはできませんどこ次々と出現してます。
(function(){
var foo = {
name: 'bob'
};
console.log(foo.name); // bob
})();
console.log(foo.name); // Reference error
実際には、上記機能は、名前なしの関数式として扱われます。
クローズとオープン括弧で機能を包むの主な目的は、グローバル空間を汚染しないようにすることです。
関数式内の変数や関数は、関数の外で使用することはできません(すなわち)プライベートになっています。
IIRC、それはあなたがプライベートプロパティとメソッドを作成することができます。