Почему .data () функция jQuery лучше для предотвращения утечек памяти?

Относительно к служебной функции jQuery jQuery.data () говорится в онлайн-документации:

"jQuery.data () метод позволяет нам присоединять данные любого типа к элементам DOM способом, который безопасен от циклических ссылок и поэтому из памяти протекает".

Почему использовать:

document.body.foo = 52; 

может закончиться утечка памяти - или в том, какие условия - так, чтобы я использовал

jQuery.data(document.body, 'foo', 52);

Я должен ВСЕГДА предпочитать .data () вместо того, чтобы использовать expandos в любом случае?

(Я ценил бы, если можно обеспечить пример для сравнения различий),

Спасибо,

burak ozdogan

7
задан pencilCake 30 April 2010 в 12:09
поделиться

3 ответа

Он лучше именно потому, что в приведенной вами цитате сказано следующее: "безопасность от круговых ссылок".

Допустим, у вас есть переменные nodeOne и nodeTwo, которые ссылаются на узлы.

Допустим, вы помещаете это в функцию (ссылку на которую вы не храните):

jQuery.data(nodeOne, 'item', nodeTwo);
jQuery.data(nodetwo, 'item', nodeOne);

После выполнения функции возникает круговая ссылка: у nodeOne есть ссылка на nodeTwo, и наоборот.

При использовании jQuery.data эта круговая ссылка не помешает сборке мусора для этих двух переменных.

Однако, если вы сделаете то же самое, но без использования jQuery.data, переменные nodeOne и nodeTwo не будут собраны в мусор, даже если они больше не нужны.

--

Должен ли я ВСЕГДА предпочитать .data() вместо вместо использования expandos в любом случае?

Если только вы не занимаетесь установкой большого количества данных и не нуждаетесь в дополнительном падении производительности (а это можно определить с помощью профилирования) и уверены, что не будете создавать круговые ссылки (или хотя бы количество, которое будет иметь значение), то да, вы можете с тем же успехом использовать только jQuery.data.

7
ответ дан 6 December 2019 в 14:01
поделиться

Немного отличного чтения на эту тему:

Memory leak patterns in JavaScript

3
ответ дан 6 December 2019 в 14:01
поделиться

Я почти уверен, что вы не можете создать утечку памяти с примитивным значением типа 52. Утечки памяти с экспандерами обычно происходят, когда применяется значение, содержащее объект с обратной ссылкой на элемент.

Советую прочитать содержание заголовка Circular Reference по адресу http://msdn.microsoft.com/en-us/library/Bb250448. А еще лучше - прочитать все :-)

Учитывая это, я думаю, что большинство людей рекомендуют не использовать expandos, если это возможно (а обычно это возможно). Использование jQuery's data() - хорошая альтернатива, в любом случае.


Только что понял, что не ответил на ваш вопрос lol. jQuery's data() предоставляет метод, который работает примерно следующим образом:
  1. jQuery вычисляет уникальный ID для данных
  2. Данные хранятся в объекте, доступном методу data(), используя уникальный ID
  3. Свойство expando применяется к элементу с уникальным ID в качестве примитивного значения

Всякий раз, когда вы вызываете data() для получения данных, jQuery обращается к свойству expando для уникального ID и использует этот ID для получения данных из объекта кэширования. Поскольку свойство expando содержит примитивное значение и не имеет привязки к объекту кэширования, никаких циклических ссылок не возникает.

5
ответ дан 6 December 2019 в 14:01
поделиться
Другие вопросы по тегам:

Похожие вопросы: