在遵循众多D3示例的同时,数据通常采用flare.json:
中给出的格式进行格式化{
"name": "flare",
"children": [
{
"name": "analytics",
"children": [
{
"name": "cluster",
"children": [
{"name": "AgglomerativeCluster", "size": 3938},
:
我有一个邻接列表如下:
A1 A2
A2 A3
A2 A4
我想转换为上面的格式。目前,我在服务器端这样做,但有没有办法使用d3的功能实现这一目标?我发现了一个here,但这种方法似乎需要修改d3核心库,由于可维护性,我不赞成。有什么建议吗?
答案 0 :(得分:54)
没有规定的格式,因为您通常可以通过各种访问器功能(例如hierarchy.children)和array.map重新定义数据。但是你引用的格式可能是树最方便的表示,因为它适用于默认的访问器。
第一个问题是您是否打算显示graph或tree。对于图表,数据结构是根据nodes和links定义的。对于树,布局的输入是根节点,其可以具有child nodes的数组,并且其叶节点具有关联的value。
如果你想显示一个图,你所拥有的只是一个边列表,那么你需要迭代边缘以产生一个节点数组和一个数组链接。假设您有一个名为“graph.csv”的文件:
source,target
A1,A2
A2,A3
A2,A4
您可以使用d3.csv加载此文件,然后生成一组节点和链接:
d3.csv("graph.csv", function(links) {
var nodesByName = {};
// Create nodes for each unique source and target.
links.forEach(function(link) {
link.source = nodeByName(link.source);
link.target = nodeByName(link.target);
});
// Extract the array of nodes from the map by name.
var nodes = d3.values(nodeByName);
function nodeByName(name) {
return nodesByName[name] || (nodesByName[name] = {name: name});
}
});
然后,您可以将这些节点和链接传递给力布局,以显示图形:
如果您想要生成树,那么您需要进行稍微不同的数据转换形式,以便为每个父级累积子节点。
d3.csv("graph.csv", function(links) {
var nodesByName = {};
// Create nodes for each unique source and target.
links.forEach(function(link) {
var parent = link.source = nodeByName(link.source),
child = link.target = nodeByName(link.target);
if (parent.children) parent.children.push(child);
else parent.children = [child];
});
// Extract the root node.
var root = links[0].source;
function nodeByName(name) {
return nodesByName[name] || (nodesByName[name] = {name: name});
}
});
像这样:
答案 1 :(得分:5)
D3不需要特定格式。这一切都取决于您的应用程序。您当然可以将邻接列表转换为flare.json中使用的格式,但这又是特定于应用程序的代码。通常,您不能这样做,因为邻接列表不具有构建树所需的“头”或“根”元素。此外,您需要单独处理周期,孤儿等。
鉴于您目前正在服务器端进行转换,我很想说“如果没有损坏,请不要修复它”;)