如何避免在Typescript中的每次使用都重复通用类型约束?

问题描述 投票:0回答:1

[在Typescript中使用泛型时,如何避免不断重复输入类型?如果我对通用类型有一些约束,那么我必须在使用通用类型的任何地方重复该约束。这很繁琐,而且不太干燥。

//A constraint on this generic
type MyConstraint = { bar: number }
type GenericOne<T extends MyConstraint> = {
    foo: T
}

为了创建一个实例,我非常讨厌重复约束,因为TS仅对函数进行一般推断

//This annoyance would I think be solved by generic values https://github.com/microsoft/TypeScript/issues/17574
const testok: GenericOne<MyConstraint> = { foo: { bar: 1 } }

现在,如果我想在其他地方使用通用类型,我也必须重复约束!

const makeGenericOne2: <T extends MyConstraint>(arg: GenericOne<T>) => GenericOne<T> = (arg) => {
    return arg
}

至少现在我可以从对象文字中创建,而无需重复我自己

const test5 = makeGenericOne2({ foo: { bar: 1 } })
// And I get nice error messsages
const test6 = makeGenericOne2({foo: {baz: 1}})

避免重复约束的唯一方法似乎是带有推断的条件类型

const makeGenericOne: <T>(arg: T extends GenericOne<infer U> ? T : never) => T = (arg) => {
    return arg
}

我仍然可以根据对象文字来创建实例,而无需重复我自己

const test3 = makeGenericOne({ foo: { bar: 1 } })

但是现在错误消息不是很好。

//"number not assignable to never" instead of { baz: 1 } is missing property "bar: number"
const test4 = makeGenericOne({ foo: { baz: 1 } })

似乎需要以下内容-推断T,因为我们知道它必须扩展Myconstraint

const propagateGeneric: <infer T>(arg: GenericOne<T>) => GenericOne<T>

很遗憾,目前TS中不允许这样做。

我如何“传播”对泛型类型的约束,以避免在使用泛型类型的所有地方重复该约束?

Sandbox Link

typescript generics type-inference typescript-generics
1个回答
0
投票

棘手,但似乎可行

//A constraint on this generic
type MyConstraint = { bar: number }
type GenericOne<T extends MyConstraint = MyConstraint> = {
    foo: T
}
© www.soinside.com 2019 - 2024. All rights reserved.