在下面的代码示例中,目的是scrapeMovies函数只接受可序列化的对象.
/* @flow */
type SerializableObjectType = {
[key: string]: string | number | boolean | $ReadOnlyArray<SerializableObjectType> | SerializableObjectType
};
type GuideType = {|
rid: string
|};
const guide: GuideType = {
rid: 'foo'
};
const scrapeMovies = async (guide: SerializableObjectType) => {};
scrapeMovies(guide);
我不明白flowtype是什么原因抱怨scrapeMovies被送入指南对象,这是一个不太严格的SerializableObjectType定义.
什么是在这里定义子类型的正确方法?
最佳答案 传递GuideType代替SerializableObjectType是传递更具体类型的实例.默认情况下,Flow仅允许函数中的
less specific(逆变/只写)输入.
要使其工作,您需要将指南参数标记为covariant.通过将对象标记为$ReadOnly<T>
,您将有效地将其标记为协变:
(Try)
type SerializableObjectType = {
[key: string]: string | number | boolean | $ReadOnlyArray<SerializableObjectType> | SerializableObjectType
};
type GuideType = {|
rid: string
|};
const guide: GuideType = {
rid: 'foo'
};
const scrapeMovies = async (guide: $ReadOnly<SerializableObjectType>) => {};
scrapeMovies(guide);
或者,您可以使用对象类型声明中的符号标记specific properties as covariant/read-only:
(Try)
type SerializableObjectType = {
+[key: string]: string | number | boolean | $ReadOnlyArray<SerializableObjectType> | SerializableObjectType
};
type GuideType = {|
rid: string
|};
const guide: GuideType = {
rid: 'foo'
};
const scrapeMovies = async (guide: SerializableObjectType) => {};
scrapeMovies(guide);
你为什么要跳这个舞?为什么输入是协变/逆变/ whateverariant很重要?好吧,如果您尝试将指南参数视为SerializeableObjectType(一般对象图),并且您为rid键写了一个数字,那么该指南对象的其他使用者将无法获得他们期望的内容.