2013-01-08 48 views
2

我一直在寻找另一个计算器的问题,我试过如下:。每个()与过滤

d3.selectAll(links.filter(function(db) { 
    return db.source.id == 'foo' 
})).each(function(p) { 
     console.log (p.source.id) 
    }) 

,发现它返回一个

TypeError: Cannot read property 'source' of undefined

即使过滤选择来作为具有.source.id值的对象的适当数组(本示例使用在D3的强制定向网络中找到的标准链接符号)。

我只是好奇,为什么这是行不通的。

回答

6

就这两个以下方法使用的是确定你是清楚的:

https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/Array/filter https://github.com/mbostock/d3/wiki/Selections#wiki-filter

的d3.selectAll函数接受一个选择器字符串或一个DOM节点数组。你的情况是哪一个?

https://github.com/mbostock/d3/wiki/Selections#wiki-d3_selectAll

记住的是,在selection.each()回调函数变量p对应于绑定到在所述选择中的元素的数据。

https://github.com/mbostock/d3/wiki/Selections#wiki-each


UPDATE

您的链接变量似乎是常规的JavaScript对象的数组。这是不正确的,因为d3.selectAll函数需要DOM节点(或选择器字符串)的数组。有趣的是,如果您使用常规数组作为参数,它不会投诉;例如,你仍然可以调用selection.each方法:

selection.each(function)

Invokes the specified function for each element in the current selection, passing in the current datum d and index i, with the this context of the current DOM element. This operator is used internally by nearly every other operator, and can be used to invoke arbitrary code for each selected element. The each operator can be used to process selections recursively, by using d3.select(this) within the callback function.

然而,因为选择不是DOM的真正选择节点以及绑定到这些数据,可以看到,在函数的第一个参数(通常ð,在你的情况p)将是未定义的。

第二个参数,所述索引i,将仍然对应于我们所遍历原始数组的索引。这就是为什么d3.selectAll(links).each(function(p, i) { console.log(links[i].source.id); })为你工作的原因。它基本上是做同样的,因为这(非D3)JavaScript表达式:中links.forEach(function(v, i) { console.log(links[i].source.id); })

一个更简单的例子你在看:

// anti-pattern: 
var arr = ['a', 'b', 'c']; 
d3.selectAll(arr) 
    .each(function(d, i) { 
     console.log(d, i, arr[i]); 
    }); 

哪些日志到控制台:

undefined 0 "a" 
undefined 1 "b" 
undefined 2 "c" 

所以,相反,如果您尝试检查强制布局的链接,您可以选择代表这些链接的DOM节点。取包含在D3库中的标准力例如:http://d3-example.herokuapp.com/examples/force/force.htm和从控制台运行以下:

d3.selectAll('line') 
    .each(function(d, i) { 
     console.log(d.source.index); 
    }); 
+0

此:d3.selectAll(链接)。每个(函数(P,I){的console.log(链接[我] .source。id)})以及像它这样的变体work,表明选择正在工作(在这种情况下,它选择一个数组),但是p变量会继续回到undefined,即使没有上面的过滤器。 – Elijah

+0

查看更多答案。 – nautat

+0

啊哈!感谢这个解释,这非常有道理。 – Elijah