ホームページ ウェブフロントエンド jsチュートリアル JavaScript 関数クロージャーの使用に関する詳細な説明とコードの詳細な説明

JavaScript 関数クロージャーの使用に関する詳細な説明とコードの詳細な説明

Jul 25, 2017 pm 03:04 PM
javascript js 予防

クロージャを表す英語はクロージャです。クロージャは JavaScript の知識の非常に重要な部分です。クロージャを使用すると、コードの量が大幅に削減され、コードがより明確に見えるなどの効果が得られます。つまり、クロージャは非常に強力です。

クロージャの意味: 端的に言えば、クロージャは関数の入れ子です。外側の関数が実行されている場合でも、内側の関数は外側の関数のすべての変数を使用できます (これには JavaScript スコープ チェーンが関係します)。

例 1

function checkClosure(){
    var str = 'rain-man';
    setTimeout(
        function(){ alert(str); } //这是一个匿名函数
    , 2000);
}
checkClosure();
ログイン後にコピー

この例は非常に単純に見えますが、実行プロセスを注意深く分析した後でも、まだ多くの知識ポイントがあります。checkClosure 関数の実行は瞬時に行われ (おそらく 0.00001 ミリ秒しかかかりません)、関数内で作成されます。 checkClosure の本体 変数 str が取得されます。これは、setTimeout の匿名関数が str への参照を持っているためです。 2 秒後、関数本体内の匿名関数が実行され、str が解放されます。

例 2、コードの最適化

function forTimeout(x, y){
    alert(x + y);
}
function delay(x , y  , time){
    setTimeout('forTimeout(' +  x + ',' +  y + ')' , time);    
}
/**
 * 上面的delay函数十分难以阅读,也不容易编写,但如果使用闭包就可以让代码更加清晰
 * function delay(x , y , time){
 *     setTimeout(
 *         function(){
 *             forTimeout(x , y) 
 *         }          
 *     , time);   
 * }
 */
ログイン後にコピー

匿名関数の最大の用途は、クロージャ (JavaScript 言語の機能の 1 つ) を作成することです。また、名前空間を構築してグローバル変数の使用を減らすこともできます。

例 3:

var oEvent = {};
(function(){ 
    var addEvent = function(){ /*代码的实现省略了*/ };
    function removeEvent(){}
    oEvent.addEvent = addEvent;
    oEvent.removeEvent = removeEvent;
})();
ログイン後にコピー

例 4:

var rainman = (function(x , y){
    return x + y;
})(2 , 3);
/**
 * 也可以写成下面的形式,因为第一个括号只是帮助我们阅读,但是不推荐使用下面这种书写格式。
 * var rainman = function(x , y){
 *    return x + y;
 * }(2 , 3);
 */
ログイン後にコピー

ここでは、変数 Rainman を作成し、匿名関数を直接呼び出すことでそれを 5 に初期化します。この小さなトリックは、場合によっては非常に実用的です。

例 5:

var outer = null;
(function(){
    var one = 1;
    function inner (){
        one += 1;
        alert(one);
    }
    outer = inner;
})();
outer();    //2
outer();    //3
outer();    //4
ログイン後にコピー

このコードの変数 1 はローカル変数 (関数内で定義されているため) であるため、外部からアクセスできません。ただし、ここでは変数 one にアクセスできる inner 関数を作成し、グローバル変数 external は inner を参照するため、outer を 3 回呼び出すと増分結果がポップアップされます。

注: クロージャにより、内部関数は親関数内の変数を参照できますが、変数は最終値です

例 6:

/**
 * <body>
 * <ul>
 *     <li>one</li>
 *     <li>two</li>
 *     <li>three</li>
 *     <li>one</li>
 * </ul>
 */
var lists = document.getElementsByTagName('li');
for(var i = 0 , len = lists.length ; i < len ; i++){
    lists[ i ].onmouseover = function(){
        alert(i);    
    };
}
ログイン後にコピー

各 <li&rt; 要素の上にマウスを移動すると、期待していた要素の添字ではなく、常に 4 が表示されます。どうしてこれなの?注意事項(最終値)に記載済みです。明らかに、この説明は単純すぎます。mouseover イベントが listen 関数を呼び出すと、まず匿名関数 (function(){alert(i); }) 内を検索して、i が定義されているかどうかを確認します。 ; したがって、上方向に検索して結果は定義されており、i の値は 4 (ループ後の i 値) であるため、最終的には毎回 4 が表示されます。

解決策 1:

var lists = document.getElementsByTagName(&#39;li&#39;);
for(var i = 0 , len = lists.length ; i &lt; len ; i++){
    (function(index){
        lists[ index ].onmouseover = function(){
            alert(index);    
        };                    
    })(i);
}
ログイン後にコピー

解決策 2:

var lists = document.getElementsByTagName(&#39;li&#39;);
for(var i = 0, len = lists.length; i &lt; len; i++){
    lists[ i ].$$index = i;    //通过在Dom元素上绑定$$index属性记录下标
    lists[ i ].onmouseover = function(){
        alert(this.$$index);    
    };
}
ログイン後にコピー

解決策 3:

function eventListener(list, index){
    list.onmouseover = function(){
        alert(index);
    };
}
var lists = document.getElementsByTagName(&#39;li&#39;);
for(var i = 0 , len = lists.length ; i &lt; len ; i++){
    eventListener(lists[ i ] , i);
}
ログイン後にコピー

以上がJavaScript 関数クロージャーの使用に関する詳細な説明とコードの詳細な説明の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。

ホットな記事タグ

メモ帳++7.3.1

メモ帳++7.3.1

使いやすく無料のコードエディター

SublimeText3 中国語版

SublimeText3 中国語版

中国語版、とても使いやすい

ゼンドスタジオ 13.0.1

ゼンドスタジオ 13.0.1

強力な PHP 統合開発環境

ドリームウィーバー CS6

ドリームウィーバー CS6

ビジュアル Web 開発ツール

SublimeText3 Mac版

SublimeText3 Mac版

神レベルのコード編集ソフト(SublimeText3)

推奨: 優れた JS オープンソースの顔検出および認識プロジェクト 推奨: 優れた JS オープンソースの顔検出および認識プロジェクト Apr 03, 2024 am 11:55 AM

推奨: 優れた JS オープンソースの顔検出および認識プロジェクト

初めてDouyinでライブブロードキャストを開始するにはどうすればよいですか?初めてライブ配信をする際に気をつけることは何ですか? 初めてDouyinでライブブロードキャストを開始するにはどうすればよいですか?初めてライブ配信をする際に気をつけることは何ですか? Mar 22, 2024 pm 04:10 PM

初めてDouyinでライブブロードキャストを開始するにはどうすればよいですか?初めてライブ配信をする際に気をつけることは何ですか?

明朝試験で注意すべき事項の紹介 明朝試験で注意すべき事項の紹介 Mar 13, 2024 pm 08:13 PM

明朝試験で注意すべき事項の紹介

よくある質問とメモ: バッチ クエリでの MyBatis の使用 よくある質問とメモ: バッチ クエリでの MyBatis の使用 Feb 19, 2024 pm 12:30 PM

よくある質問とメモ: バッチ クエリでの MyBatis の使用

簡単な JavaScript チュートリアル: HTTP ステータス コードを取得する方法 簡単な JavaScript チュートリアル: HTTP ステータス コードを取得する方法 Jan 05, 2024 pm 06:08 PM

簡単な JavaScript チュートリアル: HTTP ステータス コードを取得する方法

ネットワークなしで pip をインストールする手順と注意事項 ネットワークなしで pip をインストールする手順と注意事項 Jan 18, 2024 am 10:02 AM

ネットワークなしで pip をインストールする手順と注意事項

jsとvueの関係 jsとvueの関係 Mar 11, 2024 pm 05:21 PM

jsとvueの関係

localstorage を使用してデータを保存する手順と注意事項 localstorage を使用してデータを保存する手順と注意事項 Jan 11, 2024 pm 04:51 PM

localstorage を使用してデータを保存する手順と注意事項

See all articles