質問: jqueryでクリックイベントを拾いたいような場合、 以下の記述で可能かと思います。 ``` $(【セレクタ】).o n('click', function () { // 何かの処理 }); ``` しかし、上記の場合、後から追加されたHTMLについては クリックイベントが発動しないため、 HTMLを追加したタイミングでイベントの再読み込みが必要かと思います。 以下の記述であれば、後から追加されたHTMLについても クリックイベントが有効なのですが、 上記の記述方法に比べてパフォーマンスが悪いなどはありますでしょうか? ※部分更新を多く行いたいため本件ご質問させていただきました。 ``` $(document).on('click', '【セレクタ】', function () { // 何かの処理 }); ``` お手数ですが、ご存じの方いらっしゃいましたらご教示ください。
回答: ### イベントバブリング 理論上はイベントバブリングによってルートノード(`document`)に辿り着くまでに伝播する数だけパフォーマンスに差が出ます。 * jQuery(document) でイベントバブリング - JSFiddle ``` sample bar bar bar bar ``` 上記HTMLでは「li -> ul -> main -> body -> html -> document」と伝播されます。 伝播する数を抑える為にはより対象の要素ノードに近い場所にイベント定義する必要があります。 この例でいえば、`#foo` でイベント定義すればいいでしょう。 * jQuery('#foo') でイベントバブリング - JSFiddle ``` jQuery('#foo').on('click', '.bar', function (event) { console.log(event.type); }); ``` 上記コードを適用するには `` 直前にコードを書くか、`jQuery(function () {})` 内に定義する必要があります。 伝播する数を0にするには `.bar` 自身にイベント定義しなければなりません。 * jQuery('.bar') でイベントバブリング - JSFiddle ``` jQuery('.bar').on('click', function (event) { console.log(event.type); }); ``` この場合、動的に `` が挿入された要素ノードまでは対応できませんので、動的に要素ノードを追加する処理の方でイベント定義する必要があります。 ### MutationObserver `MutationObserver` を使用すれば、動的に要素ノードが挿入されたタイミングでイベント定義する事が可能です。 ただし、**要素ノードが追加される度に MutationObserver のチェック処理が走る**事になり、全ての要素ノードの挿入処理のパフォーマンスが低下します。 つまり、他の機能でノード挿入処理があった場合、そちらのノード挿入処理のパフォーマンスも低下してしまいます。 他のノード挿入時のパフォーマンス低下を防ぐ為には「`.bar` を挿入処理となるコード」に「clickイベント定義処理」となるコードを追加する必要があります。 ### メモリ イベントを定義した数だけメモリを消費する事になります。 ルートノード(`document`)にイベント定義すればメモリ消費量はわずかですが、各要素ノード(`.bar`)にイベント定義すれば、`.bar` の存在する数だけ比例してメモリ消費量は増えます。 従って、対象の要素数が膨大になる場合はメモリを圧迫してパフォーマンスに影響が出る可能性があります。 ### jQuery 当然ですが、jQueryの独自処理分もコストがかかります。 素のJavaScriptで書けば、より高いパフォーマンスが得られます。 * document.getElementById('foo').addEventListener でイベントバブリング - JSFiddle ``` document.getElementById('foo').addEventListener('click', function (event) { var li = event.target; if (li.classList.contains('bar')) { console.log(event.type); } }, false); ``` ### パフォーマンス検証 最終的にはバランスです。 適用されるHTML/CSSによってもパフォーマンスが変わってくるので、実際にコードを書いて動かしてパフォーマンスを比較してみるのが一番だと思います。 Re: hoshiimohunda さん