2013-03-25 52 views
1

新的数据点试想一下,我在我的代码如下电话:绑定只为性能优化

svg.selectAll("path") 
    .data(data, key) 
    .enter().append("path") 
    .attr("d", path); 

代码一段时间后,完全相同的调用时,只有data包含一些新的条目。如何将新数据条目绑定到新路径而不重绘现有路径? (即,与现有路径关联的数据元素不会改变)

这是一个性能优化:data包含10,000多个条目,每个调用添加或删除的条目少于1%。正如你可能想象的那样,绘制超过10,000条路径的资源非常密集,需要几秒钟才能完成(在此期间整个页面对用户事件没有响应)。

一种解决方案是构建旧数据和新数据之间差异的数组,并仅在新数据元素上使用enter()。但是,在提供第二个数据集时,旧的data变量在范围内变得很棘手。我认为D3必须以某种方式内部维护旧数据的表示,当然我们可以使用它。

类似地,删除的数据元素必须发生相同的过程(每个调用将从data中删除一些元素,并且必须从DOM中删除相应路径而不触及所有其他路径)。不过,我想我可以在第一部分给出解决方案时弄清楚这部分。

+0

使用enter/transition/exit join结构(http://bost.ocks.org/mike/join/)重绘所有现有路径吗? – 2013-03-25 22:30:42

+1

等等...在上面包含的代码片段中,实际上只是绘制了新元素 - “enter()”返回的元素。这里唯一涉及到任何旧元素的d3动作是'data()'操作,它决定哪些元素是新的(即输入)以及哪些元素被更新。所以这听起来像它已经在做你想做的。没有? – meetamit 2013-03-25 22:37:02

回答

1

我建议您在d3中阅读object constancyjoins

你举不仅为新的数据,基本上可以用selection.data(newDataArray, function(d){return d.id}),那么,selection.enter()会给你所有元素,给数据的新阵列的enter()功能selection.exit()所有删除元素和selection将为您提供新数据集中的所有元素(旧+新)。

Here也是一个不错的简短教程。

您可能还想看看关于d3.js中的数据的reference documentation

+0

啊,明白了。所以这非常简单!谢谢。 – 2013-03-26 00:29:45