我对打字稿很陌生,我正在尝试编写一些代码,这些代码从不同来源获取许多不同形状的数据,并将它们传递给将它们聚合的类(每个数据形状一个聚合器类)。
为此,我相信我需要一个函数(dispatch
下面称为),它将采用通用类型的数据和该数据的聚合器类的标识符,但我正在努力限制参数足以让 typescript 满意。
这是我到目前为止:
enum SourceIdentifier {
A = 'a',
B = 'b'
}
interface DataA {
prop1: number,
prop2: number[],
}
interface DataB {
prop3: number,
prop4: number,
}
class BaseAggregator<Data> {
public add(data: Data) {
// Store the data to be aggregated.
}
}
class AggregatorA extends BaseAggregator<DataA> {}
class AggregatorB extends BaseAggregator<DataB> {}
const managers = {
[SourceIdentifier.A]: new AggregatorA(),
[SourceIdentifier.B]: new AggregatorB()
}
// How to correctly constrain this function?
const dispatch = (data, source: SourceIdentifier) => {
managers[source].add(data);
};
我试过使用泛型,但遇到打字稿错误:
const dispatch = <Data, Manager extends BaseAggregator<Data>>(data: Data, source: SourceIdentifier) => {
/*
* Type 'AggregatorA | AggregatorB' is not assignable to type 'Manager'.
* 'Manager' could be instantiated with an arbitrary type which could be unrelated to 'AggregatorA | AggregatorB'
*/
const manager: Manager = managers[source];
manager.add(data);
};
是否真的可以约束这样的函数,还是由于运行时不存在的类型而注定了我的命运?谢谢,任何帮助表示赞赏。
我已经设法通过使用像这样的鉴别器来实现我想要的:
enum SourceIdentifier {
A = 'a',
B = 'b'
}
interface DiscriminatedData {
discriminator: SourceIdentifier;
}
interface DataA extends DiscriminatedData {
discriminator: SourceIdentifier.A,
prop1: number,
prop2: number[],
}
interface DataB extends DiscriminatedData {
discriminator: SourceIdentifier.B,
prop3: number,
prop4: number,
}
type DataMessage = DataA | DataB;
class BaseAggregator<Data> {
public add(data: Data) {
// Store the data to be aggregated.
}
}
class AggregatorA extends BaseAggregator<DataA> {}
class AggregatorB extends BaseAggregator<DataB> {}
const managers = {
[SourceIdentifier.A]: new AggregatorA(),
[SourceIdentifier.B]: new AggregatorB()
}
const dispatch = (data: DataMessage) => {
const manager: BaseAggregator<unknown> = managers[data.discriminator];
manager.add(data);
};
// Example
dispatch({discriminator: SourceIdentifier.A, prop1: 2, prop2: [3, 3]})
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句