我一直在阅读有关泛型的内容,并希望了解泛型如何在流程中工作。
https://flow.org/en/docs/types/generics/#toc-function-types-with-generics
我特别感兴趣的是使用flow来检查功能编程的函数签名。
但是我无法理解为什么以下不起作用:
当我尝试
时/* @flow */
const identity = (c) => c;
(identity: <T>(T) => T); // force flow to typecheck
然后Flow返回错误:
3: const identity = (c) => c;
^ T. This type is incompatible with
5: (identity: <T>(T) => T);
^ some incompatible instantiation of `T`
我原以为是因为c总是c并且没有变异,所以它的类型必须与模式匹配?
问:我如何表示该函数必须返回与第一个参数相同的类型?
免费示例
即使我尝试使用类型别名,它似乎也不起作用。
/* @flow */
type ReturnsSameTypeAsFirstParam = <T>(T) => T;
const identity:ReturnsSameTypeAsFirstParam = (c) => c;
然后我得到:
4: const identity:ReturnsSameTypeAsFirstParam = (c) => c;
^ T. This type is incompatible with
4: const identity:ReturnsSameTypeAsFirstParam = (c) => c;
^ some incompatible instantiation of `T`
我主要希望为函数提供一个类型作为参数,并了解如何以多态方式使用它们。
也许这是我想要输入的那种东西的更清晰的例子:
/* @flow */
type Transformer = <T>(T)=>T;
function transformAGivenThing(transform:Transformer, thing:*) {
return transform(thing);
}
function transformAString(str:string):string {
return str.toUpperCase();
}
transformAGivenThing(transformAString, 'thing');
当我运行flow时,这会导致这些错误:
3: type Transformer = <T>(T)=>T;
^ T. This type is incompatible with the expected param type of
9: function transformAString(str:string):string {
^ string
9: function transformAString(str:string):string {
^ string. This type is incompatible with the expected param type of
13: transformAGivenThing(transformAString, 'thing');
^ some incompatible instantiation of `T`
答案 0 :(得分:0)
关于添加到您的帖子进行了编辑。
/* @flow */
const isStr = (str: string) => !!str;
const isNmbr = (nmbr: number) => !!nmbr;
function transformAny<T>(transformer: (T) => T, thing: T): T {
return transformer(thing);
}
function transformString(thing: string): string {
return !!thing ? thing.toUpperCase() : thing;
}
function transformNumber(thing: number): number {
return !!thing ? thing * 10 : thing;
}
let s = transformAny(transformString, "1");
let n = transformAny(transformNumber, 5);
isStr(s);
// isStr(n);
// isNmbr(s);
isNmbr(n);
取消注释2次类型检查调用将引发错配匹配参数类型的错误。我不认为您可以为其中一个参数声明自定义类型并返回相应的类型。这是我第一次看到这种语言,但它看起来与TypeScript非常相似。
答案 1 :(得分:0)
好的,所以我最后提交了一个问题,要求提供方法。他们的答案是:
/* @flow */
type Transformer<T> = (T)=>T;
function transformAGivenThing(transform:Transformer<*>, thing:*) {
return transform(thing);
}
function uppercaseAString(str:string):string {
return str.toUpperCase();
}
console.log(transformAGivenThing(uppercaseAString, 'thing'));
https://github.com/facebook/flow/issues/4429
发生的事情是您需要使用Type配置Transformer
泛型类型,但在这种情况下,因为它需要是多态的,配置应该是*