問題は、誰もが「メモリ リーク」について知っていることです。一般的なシナリオはいくつかあります。
ポイント 3 は私の注意を引きました。その意味はよくわかります。たとえば、「DOM ノードを手動で削除し、DOM ノードが占有していたメモリを解放する必要があるが、不注意により、一部のコードに削除されたノードへの参照が残っているため、最終的にノードが占有していたメモリが解放されない」とします。 <div id="ルート"> <div class="child">私は子要素です</div> <button>削除</button> </div> <スクリプト> btn = document.querySelector('button') とします。 child = document.querySelector('.child') とします。 root = document.querySelector('#root') とします。 btn.addEventListener('クリック', 関数() { root.removeChild(子) }) </スクリプト> このコードは、ボタンをクリックした後に .child ノードを削除します。クリック後にノードは確かに DOM から削除されますが、グローバル変数 child にはまだノードへの参照があるため、ノードのメモリを解放できません。 解決策: .child ノードへの参照をクリック イベントのコールバック関数に移動できます。その後、ノードが削除され、コールバック関数が終了すると、ノードへの参照は自動的にクリアされ、当然メモリ リークは発生しません。 (これは実際にはイベント内にノードが存在するかどうかをリアルタイムで検出するものです。存在しない場合、ブラウザは削除関数の実行をトリガーしません。) <div id="ルート"> <div class="child">私は子要素です</div> <button>削除</button> </div> <スクリプト> btn = document.querySelector('button') とします。 btn.addEventListener('クリック', 関数() { child = document.querySelector('.child') とします。 root = document.querySelector('#root') とします。 root.removeChild(子) }) </スクリプト> このコードは完璧ですか?いいえ。各イベントがトリガーされた後に、子ノードとルートノードへの参照が作成されるためです。メモリ消費量(気が狂いそうな人もいるだろう ボタンのクリック…)。 実際には、別の方法があります。クリック時に、現在のルート ノードに子ノードがまだ存在するかどうかを判断します。存在する場合は、削除関数を実行し、存在しない場合は何もしません。 これにより、タイトルに記載されている動作が発生します。 どう判断する? トラバース?いや、面倒すぎるよ! どういうわけか、プロトタイプ チェーンに基づいてオブジェクトを走査できる 当時のシーンを復元してみましょう。GitHub を開き、親ノードをランダムに探して取得します。 図の赤い枠は取得したい親要素、オレンジ色の枠は存在するかどうかを判定したい子要素です。 親を document.querySelector('.position-relative') とします。 子を document.querySelector('.progress-pjax-loader') にします。 ここで、取得するのは DOM ノード (配列のようなオブジェクト) であるため、操作の前に処理する必要があることに注意してください。 p_child=[...parent.children]とします。 それから console.log(p_child 内の子); ! ! ! なぜ? (この時点では、筆者はまだ事の重大さに気づいていない) 何か問題があったのではないかと思い、es6 の include API を使用して確認しました。 console.log(p_child.includes(child)); それは正しい! 通常の配列で検証してみましょう。 ? ? ? この時点で、MDN を確認することを思い出しました。 その後、次のことがわかりました。in 演算子を単独で使用すると、左側の値 (インデックスとして) に対応する値が右側のオブジェクト (プロパティとプロトタイプ) 内にあるかどうかが検出されます。 上記のコードに戻ると、次のことがわかります。 これは私たちの結論を裏付けています。 明らかに、「子要素」は「プロトタイプ チェーン上に存在する」ことと同じではありません。これは、属性とプロパティの違いという別の知識ポイントにつながります。 したがって、いくつかの「トラブル」の後、ソース コードは次のように直接記述する必要があります。 <div id="ルート"> <div class="child">私は子要素です</div> <button>削除</button> </div> <スクリプト> btn = document.querySelector('button') とします。 child = document.querySelector('.child') とします。 root = document.querySelector('#root') とします。 r_child = [...root.children] とします。 btn.addEventListener('クリック', 関数() { if(r_child.includes(child)){ // または、child が null かどうかを確認することもできます... root.removeChild(child) } }) </スクリプト> やや急ぎの結末 だから、読書や勉強は「徹底的に理解しようとしない」というわけにはいかないのです~ また、「面倒なことをする」勇気と、「書類を確認する」方法を学ぶ勇気も必要です [/ 面白い顔]。 要約する 問題の JS 演算子に関するこの記事はこれで終わりです。問題の JS 演算子に関する詳細については、123WORDPRESS.COM の以前の記事を検索するか、以下の関連記事を引き続き参照してください。今後とも 123WORDPRESS.COM をよろしくお願いいたします。 以下もご興味があるかもしれません:
|
<<: Alibaba Cloud で MySQL リモート接続を構成するための詳細な手順
>>: ウェブサイトがhttpsを有効にした後のSSLのセキュリティ構成と検出
Linux 上の LibreOffice で Microsoft ドキュメントを開くと、フォントが少...
オーディオおよびビデオ ファイルを保存するためのディスク寿命を延ばすには、ディスクをフォーマットする...
Web デザインは科学であると同時に芸術でもあります。 Web デザイン作業は、半分は適切なプログラ...
序文仕事では、Linux 環境で操作する必要があることがよくあります。ここでは、win10 システム...
<br /> テキスト、シンボル、リンクの 3 つの側面に焦点を当て、主に中国語で、私の...
目次序文プロジェクトを初期化するデザインコードの実装オンデマンドロードオーディオを再生録音長押しイベ...
Linux では、通常、ファイルの名前を変更するために mv コマンドを使用します。これは、単一のフ...
HTML CSS および JavaScript を使用して、プラス、マイナス、ゼロの 3 つのボタン...
1. 同時実行性同時実行性は OLTP データベースの最も重要な機能ですが、同時実行性にはリソース...
1. Windows 版の Docker をインストールしたら、Docker クイックスタート ター...
目次序文1. 新しいパーティションを準備する2. ブートパーティションをコピーする3. fstabフ...
1. ポート 80 が占有されているかどうかを確認します。通常、ポート 80 は Apache サー...
デフォルトでは、表のタイトルは水平方向に中央揃えされます。ALIGN 属性を使用して、タイトル テキ...
CSS3 は反転可能なホバー効果を実装します。具体的なコードは次のとおりです。 1.css /*基本...
まずエラーコードを見てみましょう。 html: <テーブルボーダー="1"...