我需要将一些数据与HTML元素相关联,希望避免任何内存泄漏.显然,一个简单的解决方案是在元素上抛出某种标识符,然后创建一个字典映射,将该标识符映射到我需要的数据.但是,这是在用户将添加到其页面的javascript库中,因此我无法控制何时添加或删除元素.
我想要做的是将数据与页面上的HTML元素相关联,同时允许在删除元素时将数据用于GC.有没有办法做到这一点,不涉及编写我自己的定期GC来清理孤立的数据?向HTML元素添加属性是否安全?
Ori*_*iol 10
属性方法
您可以使用自定义data-*属性将数据存储在元素中.
这有一个限制,你只能存储字符串,但你可以使用JSON来存储普通对象或数组(而不是通过引用).
为避免与其他代码冲突,最好在属性中包含库的名称.
它们可以直接在HTML中设置:
<div data-mylibrary-foo="bar"></div>
Run Code Online (Sandbox Code Playgroud)
它们可以使用JavaScript读取或写入:
element.getAttribute('data-mylibrary-foo'); // read (old way)
element.setAttribute('data-mylibrary-foo', 'bar'); // write (old way)
element.dataset.mylibraryFoo; // read (new way)
element.dataset.mylibraryFoo = 'bar'; // write (new way)
Run Code Online (Sandbox Code Playgroud)
它们也可以通过CSS使用某些属性选择器读取.
财产方法
这比属性方法灵活得多,允许在元素中存储任意数据.
为避免与其他代码冲突,最好使用库的名称包装对象中的所有属性:
element.mylibrary = {};
element.mylibrary.foo = 'bar';
Run Code Online (Sandbox Code Playgroud)
问题是未来的HTML标准可以定义mylibrary为本机属性,因此可能存在问题.
符号方法
ECMAScript 6引入了符号,可用作属性.优点是每个符号都具有唯一的标识,因此您无需担心使用与代码相同的属性的其他库或未来标准.
var foo = Symbol("foo");
element[foo] = 'bar';
Run Code Online (Sandbox Code Playgroud)
弱地图方法
ECMAScript 6引入了WeakMap,它允许您以一种方式将数据与对象相关联,如果对象不再在其他地方被引用,则它们将被垃圾收集.
与属性方法一样,它们允许您存储任意数据.
由于数据不存储在元素本身中,因此不存在冲突风险.
var allData = new WeakMap();
var data1 = allData.get(element1) || {}; // read
data1.foo = "bar";
allData.set(element1, data1); // write
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1142 次 |
| 最近记录: |