给定一个Person
类型
type Person = {
name: string,
age: number,
address: {
line1: string,
line2: string | null | number,
zip: string | number,
},
};
我想申请重写和修改此接口。
type PersonOverwrites = {
address: {
line2?: string,
zip: string,
},
};
从这两个接口,我想创建此:
type PersonModified = {
name: string,
age: number,
address: {
line1: string,
line2?: string,
zip: string,
},
}
这就是我要找:
type PersonModified = Overwrite<Person, PersonOverwrites>
如何建立这种类型的通用的?
更新
这应该抱怨:
type DeepMerge<T, U> = [T, U] extends [object, object] ?
{
[K in keyof (U & Pick<T, Exclude<keyof T, keyof U>>)]: (
K extends keyof U ? (
K extends keyof T ? DeepMerge<T[K], U[K]> : U[K]
) : (
K extends keyof T ? T[K] : never
)
)
} : U;
type Person = {
name: string,
age: number,
address: {
line1: string,
line2: string | null | number,
zip: string | number,
address?: {
line1: string,
line2: string | null | number,
zip: string | number,
address?: {
line1: string,
line2: string | null | number,
zip: string | number,
},
},
},
};
type PersonOverwrites = {
address: {
line2?: string,
zip: string,
address?: {
address: {
pizzaDelivery: boolean,
},
},
},
};
const person: Person = {
name: 'Thomas',
age: 12,
address: {
line1: 'hi',
line2: 'hi',
zip: 'hi',
address: {
line1: 'hi',
line2: 'hi',
zip: 'hi',
address: {
line1: 'hi',
line2: 'hi',
zip: 'hi',
// pizzaDelivery: true,
}
}
}
}
我不知道你想这是多么深刻嵌套的,但你可能想是这样的:
type DeepMerge<T, U> = [T, U] extends [object, object] ?
{
[K in keyof (U & Pick<T, Exclude<keyof T, keyof U>>)]: (
K extends keyof U ? (
K extends keyof T ? DeepMerge<T[K], U[K]> : U[K]
) : (
K extends keyof T ? T[K] : never
)
)
} : U;
type PersonModified = DeepMerge<Person, PersonOverwrites>
这个想法是,DeepMerge<T, U>
计算结果为刚刚U
如果任T
或U
不是对象类型,或者它走过T
或U
每个组合键,更深入地融合。围绕如何确定哪些属性应该是可选的,以及它如何决定何时停止合并的细节是简单,但繁琐的解释。如果你需要的东西具体阐述,让我知道。
您可以验证PersonModified
相当于
type PersonModified = {
address: {
line2?: string | undefined;
zip: string;
line1: string;
};
name: string;
age: number;
}
为你想。
希望帮助;祝好运!
@jcalz答案的建设,我相信这能解决问题可选。
type Merge<M, N> = Omit<M, Extract<keyof M, keyof N>> & N;
type DeepMerge<T, U> = [T, U] extends [object, object] ?
{
[K in keyof (Merge<T, U>)]: (
K extends keyof U ? (
K extends keyof T ? DeepMerge<T[K], U[K]> : U[K]
) : (
K extends keyof T ? T[K] : never
)
)
} : Merge<T, U>;