我遇到了以下问题:
type NonUndefined<T> = T extends undefined ? never : T;
enum TestEnum {
T1 = "T1",
T2 = "T2",
}
interface Data {
Val: TestEnum;
}
type AltFormData<T> = T extends object
? {
readonly [P in keyof T]-?: AltFormData<NonUndefined<T[P]>>;
} & AltFormValue<NonUndefined<T>>
: AltFormValue<NonUndefined<T>>;
type Alt1FormData<T> = AltFormValue<NonUndefined<T>>;
type Alt2FormData<T> = T extends object ? AltFormValue<NonUndefined<T>> : AltFormValue<NonUndefined<T>>;
type AltFormValue<T = any> = {
readonly $setValue: (value: T | undefined) => void;
};
const x2: AltFormData<Data> = {};
x2.Val.$setValue(TestEnum.T1); // ERROR - x2.Val is of type AltFormValue<TestEnum.T1> | AltFormValue<TestEnum.T2> and should be of type AltFormValue<TestEnum>
const x3: AltFormValue<TestEnum> = {};
x3.$setValue(TestEnum.T1); // GOOD
const x4: AltFormData<TestEnum> = {};
x4.$setValue(TestEnum.T1); // ERROR - x4 is of type AltFormValue<TestEnum.T1> | AltFormValue<TestEnum.T2> and should be of type AltFormValue<TestEnum>
const x5: AltFormValue<NonUndefined<TestEnum>> = {};
x5.$setValue(TestEnum.T1); // GOOD
const x6: Alt1FormData<TestEnum> = {};
x6.$setValue(TestEnum.T1); // GOOD
const x7: Alt2FormData<TestEnum> = {};
x7.$setValue(TestEnum.T1); // ERROR - x7 is of type AltFormValue<TestEnum.T1> | AltFormValue<TestEnum.T2> and should be of type AltFormValue<TestEnum>
似乎类型检查T extends object
改变了结果。同样的事情发生在使用类型"T1" | "T2"
而不是枚举时。您可以将此代码复制并粘贴到TS Playground中,或者只需单击链接。
1条答案
按热度按时间3duebb1j1#
看起来typescript把
enum
类型当作它的值的并集,这对条件类型有影响。所以,当你有这种类型:
然后你给它一个枚举,实际上是
TestEnum.T1 | TestEnum.T2
,typescript会计算类型。这就是Distributive conditional types,这是typescript默认处理条件中联合类型的方式,如果你不想这样,你需要关闭这个选项,把
T
和object
放到括号里.这将导致改为计算此类型:
如果进行简化,则这就是所需的类型
其别名为:
那么您就不会看到编译错误。