TypeScript问题:boolean类型无法赋值给true/false类型的解决方法
解决TypeScript字面量类型推断不匹配问题
问题原因
TypeScript 默认会将对象字面量中的true/false拓宽为通用的boolean类型,而非保留原始的字面量类型。这就导致你定义的badObj和goodObj中,ok属性的类型被推断为boolean,无法匹配Ok/Bad接口里要求的true/false字面量类型,最终出现传参类型不兼容的错误。
优化方案
方案1:显式指定对象类型
直接为badObj和goodObj标注对应的接口类型,强制TypeScript使用字面量类型而非拓宽后的boolean:
interface Ok { ok: true; date: undefined; } interface Bad { ok: false; date: Date; } // 显式指定类型 const badObj: Bad = { ok: false, date: new Date()}; const goodObj: Ok = { ok: true, date: undefined} const fn = (obj: Ok | Bad) => { console.log(obj.ok); if (!obj.ok) { const minutes = obj.date.getMinutes(); // 类型守卫生效,无报错 } }; fn(badObj) // 无报错 fn(goodObj) // 无报错
方案2:使用as const断言
通过as const断言让TypeScript保留对象的字面量类型(同时会将对象变为只读):
interface Ok { ok: true; date: undefined; } interface Bad { ok: false; date: Date; } // 用as const保留字面量类型 const badObj = { ok: false, date: new Date()} as const; const goodObj = { ok: true, date: undefined} as const; const fn = (obj: Ok | Bad) => { console.log(obj.ok); if (!obj.ok) { const minutes = obj.date.getMinutes(); // 类型守卫正常工作 } }; fn(badObj) fn(goodObj)
注意:as const会把对象的所有属性变为只读,如果需要后续修改对象属性,不建议使用此方案。
验证效果
修改后,TypeScript能正确识别badObj和goodObj符合Ok | Bad类型,函数内部的类型守卫也能正常区分两种类型,不会出现类型报错。
内容的提问来源于stack exchange,提问作者Nick Reid
相关产品推荐
相关产品推荐

