javascript getAttribute是否会影响性能或触发布局

Does javascript getAttribute affects performance or triggers layout?

本文关键字:布局 性能 影响 getAttribute 是否 javascript      更新时间:2023-09-26

我正在练习视差,所以在滚动过程中我需要元素的offsetTop和高度。我知道,每次当你"得到"这种风格的属性时,它都会触发布局,所以它会影响整体性能。我决定为每个具有功能的元素设置自定义属性,并在调整窗口大小时进行更新:

function setAttrs() {
  $sections.each(function() {
    var offsetTop = $(this).offset().top,
        height = $(this).height();
    $(this).attr({"data-offset": offsetTop, "data-height": height});
  });
}
setAttrs();
$(window).on("resize", function() {
  setAttrs();
});

所以,我的问题是,滚动处理程序中的属性getter会以某种方式影响性能吗?类似这样的东西:

var height = $(this).attr("data-height");

我有90%的把握这是个好办法,但我需要确定。

首先,这并不是设置data-*属性值的最佳方式:

$(this).data({ offset: offsetTop, height: height });

这并没有触及DOM-jQuery在其自己的数据结构中维护值。当首次从特定元素引用data-*属性时,它将读取属性,但不会在DOM中更新它们。还应参考.data():

var savedHeight = $(this).data("height");

请注意,使用.data() API时会去掉"data-"前缀。

其次,在"调整大小"处理程序中对DOM所做的任何操作都会影响性能,因为当窗口以交互方式调整大小时,浏览器会非常迅速地触发"调整大小(resize)"。通常,最好确保您的"调整大小"处理程序最多每50或100毫秒只做一次工作。根据你想要达到的效果,有几种不同的方法可以做到这一点。

当您谈论性能时:

由于您在each回调中的三个位置使用$(this),因此最好将其存储在变量中。这也可以避免一些开销。

function setAttrs() {
  $sections.each(function() {
    var $self = $(this);
    var offsetTop = $self.offset().top,
        height = $self.height();
        $self.data({"offset": offsetTop, "height": height});
  });
}

@Pointy提到的其他事情。

派对迟到了——但我有一些基准。

至于原始Element.getAttribute,它从不引起回流。在某些浏览器中,它仍然比访问缓存数据慢得多,而在其他浏览器中则不然(jsPerf)。

然而,jQuery的$().attr总是比原生Element.getAttribute(jsPerf)慢得多。可能用另一个函数包装DOM方法会阻止浏览器进行优化——我已经遇到过这种情况。

正如其他人所指出的,$().data应该比$().attr快得多。这里有一个jsPerf,尽管由于网络问题,我无法访问结果。