検索
ホームページウェブフロントエンドjsチュートリアルクロージャーはメモリリークを引き起こすのでしょうか?

前書き

メモリ リークの問題について話す前に、JavaScript のガベージ コレクション メカニズムを見てみましょう。JavaScript には、使用されなくなった変数を見つけて、それらが占有しているメモリを解放する自動ガベージ コレクション メカニズムがあります。これを行うために、ガベージ コレクターは一定の間隔 (またはコード実行中にスケジュールされた収集時間) で動作します。一般的に使用される方法には、クリア マーキングと参照カウントの 2 つがあります。

1. マーク スイープ

JavaScript で最も一般的に使用されるガベージ コレクション方法は、マーク アンド スイープです。ガベージ コレクターは、実行時にメモリに格納されているすべての変数にマークを付けます (任意のマーク方法を使用できます)。次に、環境内の変数と環境内の変数によって参照される変数のタグを削除します。これ以降にマークされた変数は、環境内の変数がこれらの変数にアクセスできなくなるため、削除される変数とみなされます。最後に、ガベージ コレクターはメモリのクリーンアップ作業を完了し、マークされた値を破棄し、それらが占有しているメモリ領域を再利用します。

2. 参照カウント

参照カウントの意味は、各値が参照された回数を追跡することです。変数が宣言され、その変数に参照型の値が割り当てられている場合、この値への参照の数は 1 です。同じ値が別の変数に代入されている場合、その値の参照カウントは 1 増加します。逆に、この値への参照を含む変数が別の値を取得すると、この値への参照の数は 1 つ減ります。この値への参照の数が 0 になると、この値にアクセスする方法がなくなったことを意味するため、この値が占有しているメモリ領域を再利用できます。こうすることで、次回ガベージ コレクターが実行されるときに、参照がゼロの値によって占められていたメモリが解放されます。

Netscape Navigator 3.0 は、参照カウント戦略を使用した最初のブラウザでしたが、すぐに深刻な問題に遭遇しました。次の例を参照してください:

function problem(){ 
    var objectA = new Object(); 
    var objectB = new Object(); 
    objectA.someOtherObject = objectB; 
    objectB.anotherObject = objectA; 
}

説明: objectA と objectB は、それぞれの属性、つまり、両方のオブジェクトの参照カウントは 2 です。マーク アンド スイープ戦略を使用する実装では、関数の実行後に両方のオブジェクトがスコープを離れるため、この相互参照は問題になりません。ただし、参照カウント戦略を使用した実装では、objectA と objectB の参照数が 0 になることはないため、関数の実行後も存在し続けます。この関数が複数回呼び出された場合、大量のメモリはリサイクルされません。

このため、Netscape は Navigator 4.0 で参照カウント方式を放棄しましたが、参照カウントによって引き起こされる問題はこれで終わりではありませんでした。 IE 9 より前の一部のオブジェクトはネイティブ JavaScript オブジェクトではありませんでした。たとえば、BOM および DOM 内のオブジェクトは、C++ を使用して COM (コンポーネント オブジェクト モデル) オブジェクトの形式で実装され、COM オブジェクトのガベージ コレクション メカニズムでは参照カウント方式が使用されます。したがって、IE の JavaScript エンジンはマーク アンド スイープ戦略を使用して実装されていますが、JavaScript によってアクセスされる COM オブジェクトは依然として参照カウント戦略に基づいています。言い換えれば、COM オブジェクトが IE に関与する場合は常に、循環参照の問題が発生します。

例:

var element = document.getElementById("some_element"); 
var myObject = new Object(); 
myObject.element = element; 
element.someObject = myObject;

DOM 要素 (element) とネイティブ JavaScript オブジェクト (myObject) の間に循環参照が作成されます。その中で、変数 myObject には要素オブジェクトを指す element という名前のプロパティがあり、変数 element には myObject を指す someObject という名前のプロパティもあります。この循環参照のため、例の DOM がページから削除されても、リサイクルされることはありません。

解決策: 変数を null に設定して、変数と以前に参照していた値の間の接続を切断します。

myObject.element = null; 
 
element.someObject = null;

上記の内容を読んだ上で、本題についてお話しさせていただきます。

クロージャーによってメモリ リークが発生することはありません

IE9 より前のバージョンでは、JScript オブジェクトと COM オブジェクトに対して異なるガベージ コレクションが使用されるためです。したがって、これらのバージョンの IE では、クロージャによっていくつかの特別な問題が発生します。具体的には、HTML 要素がクロージャのスコープ チェーンに格納されている場合、その要素は破棄できないことを意味します。例を参照してください。

function assignHandler(){ 
    var element = document.getElementById("someElement"); 
    element.onclick = function(){ 
        alert(element.id); 
    }; 
}

上記のコードは、要素要素のイベント ハンドラとして機能するクロージャを作成します。このクロージャーは循環参照を作成します。無名関数は assignHandler() のアクティブなオブジェクトへの参照を保存するため、要素への参照の数を減らすことができなくなります。匿名関数が存在する限り、要素の参照番号は少なくとも 1 であるため、要素が占有するメモリは決してリサイクルされません

解決策は序文で述べたように、element.id のコピーを変数に保存することで、削除 クロージャ内の変数への循環参照も、要素変数を null に設定します。

function assignHandler(){ 
    var element = document.getElementById("someElement"); 
    var id = element.id; 
    element.onclick = function(){ 
        alert(id); 
    }; 
    element = null; 
}

概要: クロージャはメモリ リークを引き起こしませんが、IE9 より前のバージョンでは JScript オブジェクトと COM オブジェクトに対して異なるガベージ コレクションが使用されるため、メモリをリサイクルできません。これは IE の問題であるため、クロージャとメモリ リークは問題ではありません。 。

声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
JavaScriptとWeb:コア機能とユースケースJavaScriptとWeb:コア機能とユースケースApr 18, 2025 am 12:19 AM

Web開発におけるJavaScriptの主な用途には、クライアントの相互作用、フォーム検証、非同期通信が含まれます。 1)DOM操作による動的なコンテンツの更新とユーザーインタラクション。 2)ユーザーエクスペリエンスを改善するためにデータを提出する前に、クライアントの検証が実行されます。 3)サーバーとのリフレッシュレス通信は、AJAXテクノロジーを通じて達成されます。

JavaScriptエンジンの理解:実装の詳細JavaScriptエンジンの理解:実装の詳細Apr 17, 2025 am 12:05 AM

JavaScriptエンジンが内部的にどのように機能するかを理解することは、開発者にとってより効率的なコードの作成とパフォーマンスのボトルネックと最適化戦略の理解に役立つためです。 1)エンジンのワークフローには、3つの段階が含まれます。解析、コンパイル、実行。 2)実行プロセス中、エンジンはインラインキャッシュや非表示クラスなどの動的最適化を実行します。 3)ベストプラクティスには、グローバル変数の避け、ループの最適化、constとletsの使用、閉鎖の過度の使用の回避が含まれます。

Python vs. JavaScript:学習曲線と使いやすさPython vs. JavaScript:学習曲線と使いやすさApr 16, 2025 am 12:12 AM

Pythonは、スムーズな学習曲線と簡潔な構文を備えた初心者により適しています。 JavaScriptは、急な学習曲線と柔軟な構文を備えたフロントエンド開発に適しています。 1。Python構文は直感的で、データサイエンスやバックエンド開発に適しています。 2。JavaScriptは柔軟で、フロントエンドおよびサーバー側のプログラミングで広く使用されています。

Python vs. JavaScript:コミュニティ、ライブラリ、リソースPython vs. JavaScript:コミュニティ、ライブラリ、リソースApr 15, 2025 am 12:16 AM

PythonとJavaScriptには、コミュニティ、ライブラリ、リソースの観点から、独自の利点と短所があります。 1)Pythonコミュニティはフレンドリーで初心者に適していますが、フロントエンドの開発リソースはJavaScriptほど豊富ではありません。 2)Pythonはデータサイエンスおよび機械学習ライブラリで強力ですが、JavaScriptはフロントエンド開発ライブラリとフレームワークで優れています。 3)どちらも豊富な学習リソースを持っていますが、Pythonは公式文書から始めるのに適していますが、JavaScriptはMDNWebDocsにより優れています。選択は、プロジェクトのニーズと個人的な関心に基づいている必要があります。

C/CからJavaScriptへ:すべてがどのように機能するかC/CからJavaScriptへ:すべてがどのように機能するかApr 14, 2025 am 12:05 AM

C/CからJavaScriptへのシフトには、動的なタイピング、ゴミ収集、非同期プログラミングへの適応が必要です。 1)C/Cは、手動メモリ管理を必要とする静的に型付けられた言語であり、JavaScriptは動的に型付けされ、ごみ収集が自動的に処理されます。 2)C/Cはマシンコードにコンパイルする必要がありますが、JavaScriptは解釈言語です。 3)JavaScriptは、閉鎖、プロトタイプチェーン、約束などの概念を導入します。これにより、柔軟性と非同期プログラミング機能が向上します。

JavaScriptエンジン:実装の比較JavaScriptエンジン:実装の比較Apr 13, 2025 am 12:05 AM

さまざまなJavaScriptエンジンは、各エンジンの実装原則と最適化戦略が異なるため、JavaScriptコードを解析および実行するときに異なる効果をもたらします。 1。語彙分析:ソースコードを語彙ユニットに変換します。 2。文法分析:抽象的な構文ツリーを生成します。 3。最適化とコンパイル:JITコンパイラを介してマシンコードを生成します。 4。実行:マシンコードを実行します。 V8エンジンはインスタントコンピレーションと非表示クラスを通じて最適化され、Spidermonkeyはタイプ推論システムを使用して、同じコードで異なるパフォーマンスパフォーマンスをもたらします。

ブラウザを超えて:現実世界のJavaScriptブラウザを超えて:現実世界のJavaScriptApr 12, 2025 am 12:06 AM

現実世界におけるJavaScriptのアプリケーションには、サーバー側のプログラミング、モバイルアプリケーション開発、モノのインターネット制御が含まれます。 2。モバイルアプリケーションの開発は、ReactNativeを通じて実行され、クロスプラットフォームの展開をサポートします。 3.ハードウェアの相互作用に適したJohnny-Fiveライブラリを介したIoTデバイス制御に使用されます。

next.jsを使用してマルチテナントSaaSアプリケーションを構築する(バックエンド統合)next.jsを使用してマルチテナントSaaSアプリケーションを構築する(バックエンド統合)Apr 11, 2025 am 08:23 AM

私はあなたの日常的な技術ツールを使用して機能的なマルチテナントSaaSアプリケーション(EDTECHアプリ)を作成しましたが、あなたは同じことをすることができます。 まず、マルチテナントSaaSアプリケーションとは何ですか? マルチテナントSaaSアプリケーションを使用すると、Singの複数の顧客にサービスを提供できます

See all articles

ホットAIツール

Undresser.AI Undress

Undresser.AI Undress

リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover

AI Clothes Remover

写真から衣服を削除するオンライン AI ツール。

Undress AI Tool

Undress AI Tool

脱衣画像を無料で

Clothoff.io

Clothoff.io

AI衣類リムーバー

AI Hentai Generator

AI Hentai Generator

AIヘンタイを無料で生成します。

ホットツール

MinGW - Minimalist GNU for Windows

MinGW - Minimalist GNU for Windows

このプロジェクトは osdn.net/projects/mingw に移行中です。引き続きそこでフォローしていただけます。 MinGW: GNU Compiler Collection (GCC) のネイティブ Windows ポートであり、ネイティブ Windows アプリケーションを構築するための自由に配布可能なインポート ライブラリとヘッダー ファイルであり、C99 機能をサポートする MSVC ランタイムの拡張機能が含まれています。すべての MinGW ソフトウェアは 64 ビット Windows プラットフォームで実行できます。

SublimeText3 英語版

SublimeText3 英語版

推奨: Win バージョン、コードプロンプトをサポート!

SublimeText3 中国語版

SublimeText3 中国語版

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

SAP NetWeaver Server Adapter for Eclipse

SAP NetWeaver Server Adapter for Eclipse

Eclipse を SAP NetWeaver アプリケーション サーバーと統合します。

PhpStorm Mac バージョン

PhpStorm Mac バージョン

最新(2018.2.1)のプロフェッショナル向けPHP統合開発ツール