使用字符串文字的并集作为输入参数时,删除强制类型转换并将类型放入函数标题中会如何:
const get = <T extends "barcode" | "mqtt">(s: T) =>
s === "barcode" ?
<T extends "barcode" ? {scan: () => string} : {pan: () => string}>{scan: () => "we are scanning"} :
<T extends "barcode" ? {scan: () => string} : {pan: () => string}>{pan: () => "we are panning"}
get("barcode").scan() // OK
get("mqtt").pan() // OK
get("barcode").pan() // Error
我遇到了这个问题,试图回答别人的问题:https://stackoverflow.com/a/55059318/2684980。
答案 0 :(得分:1)
最干净的解决方案是使用重载代替这种情况(尽管没有比类型断言更安全的类型)。您可以在公共签名中使用条件类型,并在实现签名中使用简单的联合。您将需要切换到函数声明,因为函数表达式(箭头或正则表达式)不容易支持重载:
function get<T extends "barcode" | "mqtt">(s: T): T extends "barcode" ? { scan: () => string } : { pan: () => string }
function get(s: "barcode" | "mqtt"): { scan: () => string } | { pan: () => string } {
return s === "barcode" ?
{ scan: () => "we are scanning" } :
{ pan: () => "we are panning" }
}
get("barcode").scan() // OK
get("mqtt").pan() // OK
get("barcode").pan() // Error