【发布时间】:2019-04-28 06:07:58
【问题描述】:
我面临的情况是 HTTP 调用的响应因地区而异。 我已经指定了对象的返回类型。因此,如果我声明假设 4 种类型并将这些类型的并集用作包装类型。
问题出现了,因为有些字段并非对所有事物都通用。 解决方案是使这些字段或可选。 对我来说,将字段设为可选意味着没有必要在这种情况下不正确。因为这样可以让 Tslint 错误消失。
如果你没有理解我的问题,请告诉我
编辑:-
function mapAddress(address: AddressRegionXX | AddressRegionYY,region:string): AddressWithIdXX | AddressWithIdXX {
let addressId = address.id ? address.id : "XX";
let addressType = addressId == "XX" ? "subbed" : "unsubbed";
if(region == "XX"){
return {
firstName: address.first_name || null,
lastName: address.last_name || null,
street1: address.addr_1 || null,
street2: address.addr_2 || null,
city: address.city || null,
state: address.state || null,
postalCode: address.zip_code || null,
phone: address.phone_number || null,
addressId: addressId,
addressType: addressType
};
if(region == "XX"){
return {
fName: address.f_name || null,
lName: address.l_name || null,
address: address.addr_1 || null,
roomNo: address.addr_2 || null,
district: address.district|| null,
state: address.state || null,
pinCode: address.zip_code || null,
phoneNumber: address.phone_number || null,
addressId: addressId,
addressType: addressType
};
}
}
这是我必须使用联合类型的上下文 在这里,取决于每个区域地址类型的响应会发生变化,有一个很长的列表,在这里包含它是不切实际的。 正如我在这里展示的那样,每个地区的字段名称各不相同,并且还有一些额外的字段。 那么解决这种情况的优雅方法是使用条件类型。有没有联合类型的替代品。 与 ed 一样,至少有 5-6 个地址类型,未来还有更多机会。
In layman terms
is there any miraculous way in which :D
We write something Like
type correctTypeAddress<T> =
T extends Address? AddressXX :
T extends Address? AddressYY :
mapAddress(address: AddressRegion,region:string):correctTypeAddress
以下是我正在处理的所有类型不具有相同属性的示例。那么如何处理非统一类型映射
重现问题的方法
type typeA = {
prop1:string;
prop2:string;
}
type typeB = {
prop1: string;
prop3: string;
}
type typeC = {
prop4: string;
prop5: string;
}
type mappedType = typeA | typeB | typeC;
const a = (b): mappedType => {
return {
prop1:"1",
prop5:"3"
}
}
编辑:- 应用条件类型但使用泛型会导致另一个 lint 错误,如 Property 'prop1' does not exist on type 'T'
type typeIA = {
prop1: string;
prop2: string;
}
type typeIB = {
prop1: string;
prop3: string;
}
type typeIC = {
prop4: string;
prop5: string;
}
type typeOA = {
prop1: string;
prop2: string;
}
type typeOB = {
prop1: string;
prop3: string;
}
type typeOC = {
prop4: string;
prop5: string;
}
// type mappedType = typeA | typeB | typeC;
const a = <T extends typeIA | typeIB | typeIC>(_b: T): T extends typeIA ? typeOA : never | T extends typeIB ? typeOB : never | T extends typeIC ? typeOC : never=> {
if (_b.prop1 == "1"){
return {
prop1: "1",
prop3: "3"
} as T extends typeIA ? typeOA : never | T extends typeIB ? typeOB : never | T extends typeIC ? typeOC : never
}else{
return {
prop1: "1",
prop2: "2"
} as T extends typeIA ? typeOA : never | T extends typeIB ? typeOB : never | T extends typeIC ? typeOC : never
}
}
const c = a({prop1:"1",prop2:"2"});
const d = a({ prop1: "1", prop3: "2" });
const e = a({ prop4: "1", prop5: "2" });
【问题讨论】:
-
只用type guard?
-
请编辑此问题以提供您的问题的minimal reproducible example,以便有人可以提出直接解决问题的建议。否则,任何答案都只是对您所面临的实际问题的猜测。
-
@jcalz 你现在可以看看吗
-
我很想看看这个,但进入门槛仍然太高。为了使该代码甚至可以无错误地编译以开始处理答案,有人需要为
AddressRegion等类型发明接口/类型定义。你能做到吗?理想情况下,您会给我们一些代码,有人可以将它们原样放入 IDE(如the Playground)并开始进行修改和建议。唯一的错误应该是与问题相关的错误。这是minimal reproducible example 的“完整”和“可验证”部分。祝你好运! -
理想情况下,Q 和 A 应该是这样的:“Q:这里有一些代码很乏味,而且无法扩展。有没有更好的方法来做到这一点?A:这里有一些更改的代码具有相同的效果,但不那么乏味且可扩展性更好。”我要求你做 Q 部分。如果您的示例代码充满错误,那么要么我必须自己修复它们,要么我必须接受答案代码中的错误,这意味着我无法测试答案,这意味着它可能无法正常工作。我个人对建议一个我无法测试的答案感到不舒服。也许会有其他感觉不同的人出现。