Javascript 将数据存储到DOM-元素值与数据属性

Javascript 将数据存储到DOM-元素值与数据属性,javascript,jquery,html,Javascript,Jquery,Html,要在DOM元素中存储值,我们可以通过dataattribute来实现 $(“#abc”).data(“item”,1),检索do$(“#abc”).data(“item”) 但今天我知道我们也可以这样做: $(“#abc”)[0]。项=1,要检索do$(“#abc)[0]。项 它们之间有什么区别? 哪个更好?哪个兼容范围更广?.data()的存在有几个原因: 如果将JS对象放入DOM对象的属性中,某些(大部分是较旧的)浏览器会出现内存泄漏问题。这会在DOM和JS world(具有单独的垃圾收集器

要在DOM元素中存储值,我们可以通过
data
attribute来实现

$(“#abc”).data(“item”,1)
,检索do
$(“#abc”).data(“item”)

但今天我知道我们也可以这样做:

$(“#abc”)[0]。项=1
,要检索do
$(“#abc)[0]。项

它们之间有什么区别? 哪个更好?哪个兼容范围更广?

.data()
的存在有几个原因:

  • 如果将JS对象放入DOM对象的属性中,某些(大部分是较旧的)浏览器会出现内存泄漏问题。这会在DOM和JS world(具有单独的垃圾收集器)之间创建引用,从而导致问题并可能导致内存泄漏。使用
    .data()将引用完全保留在JS world中
    而不是DOM属性解决了这个问题。老实说,我不知道这在现代浏览器中还有多大问题。很难测试,更容易使用已知的安全方法

  • 历史上,某些主机对象不支持使用直接属性语法添加任意属性,例如
    obj.prop=1;
    .data()
    使您可以将数据与任何对象关联,无论其是否具有处理任意属性的能力

  • 名称冲突。
    .data()
    在一个DOM对象上创建一个且仅一个自定义属性,该属性只是一个id值(字符串)。然后,您可以自由地使用
    .data()
    中所需的任何键,无需担心与DOM对象上预先存在的属性名称冲突。
    .data()
    本质上是它自己的自定义属性名称空间

  • 读取HTML5“data xxx”属性。当您读取尚未写入实际jQuery数据存储的
    .data(“xxx”)
    属性时,jQuery将读取DOM对象上的
    “data xxx”
    属性。如果找到该属性,它将返回该值,并强制其类型,使其为“false”“转换为Javascript
    false
    。如果随后写入
    .data(“xxx”,“foo”)
    ,则该值不会覆盖到DOM对象上,而是写入到jQuery存储中,从那时起,所有未来的读写都来自jQuery
    .data()
    存储。这很有用的一个原因是自定义属性(与自定义属性不同)只能是字符串,但
    .data(“xxx”,yyy)
    可以写入和存储任何JS数据类型

  • 因此,如果要使用已知的安全方法,即使在较旧的浏览器中也不容易发生内存泄漏,请使用
    .data()
    ,而不是在DOM对象上创建自己的自定义属性

    我怀疑在将来的某个时候,浏览器可能会被认为是足够安全的,您可以将JS对象引用存储在自定义DOM属性中,而不必担心内存泄漏,此时使用
    .data()
    之类的东西的原因可能会少一些,尽管上面的问题3仍然存在


    使用
    .data()
    有一些缺点


  • 如果在
    .data()
    中存储了大量有意义的数据,然后删除了相应的DOM对象,而没有使用jQuery的方法来删除它(例如直接使用
    .removeChild()
    ,或者只在父对象上设置了
    .innerHTML
    ),则存储在
    .data()中的数据
    store将被孤立,并且永远不会被清理,因为jQuery不知道相应的DOM对象已被删除。这将导致javascript中的一些数据保存在您永远不会使用的数据结构中。虽然从技术上讲,这不是一个泄漏(因为数据仍在那里可供使用),但它具有与浪费一些内存大致相同的效果。如果使用
    .data()
    ,则应仅使用jQuery方法删除或替换DOM对象,因为它们可以防止内存浪费

  • 由于上述问题,当使用jQuery的方法可能导致删除DOM对象时,jQuery必须做额外的工作,以确保在使用自己的方法时清理
    .data()
    。这可能会降低
    .html(“xxx”)
    .remove()
    等的性能


  • “孤立且从未清理”==内存泄漏?@SimonKuang-我添加了关于该问题的更多描述。其他缺点:如果您尝试从刚刚删除的元素的突变观察者内部访问数据,Jquery数据已经消失,即使DOM元素仍然可以从观察者回调访问。