我目前正在D3(v4.4.0)和Typsecript中构建可视化,其中包含从@ types / d3安装的类型。对于可视化,我需要嵌套我的数据。我正在尝试使用此代码段,该代码段应计算每个键的条目数:
d3.nest()
.key(function(d: any) {return d.key;})
.rollup(function(leaves: any){
return d3.sum(leaves, function (d) {
return 1;
})
})
.entries(this.data);
对于汇总方法中的辅助函数,我得到一个类型错误:
severity: 'Error'
message: 'Argument of type '(leaves: any) => number' is not assignable to parameter of type '(values: {}[]) => undefined'.
Type 'number' is not assignable to type 'undefined'.'
at: '46,15'
source: 'ts'
所以看来tsc期望rollup()返回undefined,这对我来说没有意义,这段代码在纯javascript中运行良好。只是在没有汇总()的情况下嵌套数据也可以。
有人知道这里可能出了什么问题吗?
谢谢, 托马斯
答案 0 :(得分:5)
在D3 v4中,d3.nest()
工厂有几个签名。它们之间的唯一区别是,对于控制约束返回的Nest<Datum, RollupType>
生成器的数据类型的两个泛型,您可以控制多少。
由于 d3-collection 的JSDoc评论的完成仍然是一个被跟踪的待办事项,我将在此期间提供一个简短的解释。
在Nest<Datum, RollupType>
界面中,第一个通用Datum
指的是数据array
中传递给以下方法的元素的数据类型Nest
生成器:
map(...)
object(...)
entries(...)
出于同样的原因,它是key
访问器函数的参数的数据类型,并且在您的情况下,array
的元素的数据类型传递到卷 - 起作用作为论据。
因此,在调用Datum
工厂(见下文)时明确设置d3.nest()
始终是谨慎的。
第二个通用约束Nest
生成器,RollupType
仅在您打算配置/使用rollup(...)
访问器时才相关,如您的情况。它控制汇总功能的返回类型。
因此,正如您所说,由于您需要汇总功能,您应该使用以下内容,根据您的源数据类型进行嵌套:
interface YourDatum {
key: string;
// any proprties related to the value of this element
}
let data: YourDatum[];
data = [/* set your data */]
d3.nest<YourDatum, number>()
.key(function (d) { return d.key; })
.rollup(function (leaves) {
return d3.sum(leaves, function (d) {
return 1;
})
})
.entries(data);
}
请注意,传递给key
和rollup
的访问者函数受接口定义和泛型的指定类型的约束。
如果您只是在调用d3.nest()
时不使用泛型,则默认值意味着您返回Nest<{}, undefined>
。这会强制您遇到的错误为 nudge ,以确保嵌套下的数据类型对应于方法和访问器函数中的参数/返回类型。
话虽如此,但定义文件中的map(...)
,object(...)
和entries(...)
方法的 return 类型的评论较长。它揭示了嵌套过程的复杂性,即i.p。如果使用累积。你可以找到它here。
在工厂中使用泛型,现在在D3 v4定义中相当广泛。
作为最终评论,我还会跟踪DefinitelyTyped上的问题,以验证strictNullChecks
的 d3-collection 。当我有一个安静的时刻时,将与JSDoc评论联合起来......
希望这有助于解释。
答案 1 :(得分:1)
rollup()
方法的签名声明似乎是一个问题。
只需将冲突元素强制转换为any
类型,就可以忽略此错误,以及您在d3类型中找到的任何其他不一致之处:
d3.nest()
.key(function(d: any) {return d.key;})
.rollup(function(leaves: any){
return d3.sum(leaves, function (d) {
return 1;
}) as any
})
.entries(this.data);
D3 API非常庞大,因此您可能会在不那么流行的功能中发现更多这样的错误。您可以通过搜索与您找到的错误相关的already an open issue以及是否提交新问题来提供帮助。