Typescript 传递给泛型函数参数,该参数的类型是泛型的键,而对象[key]是数字

Typescript 传递给泛型函数参数,该参数的类型是泛型的键,而对象[key]是数字,typescript,generics,Typescript,Generics,我有一个通用函数: function mkSorter<T extends { [key: string]: unknown }, K extends keyof T>(prop: K) { return (a: T, b: T) => a[prop] - b[prop]; } 因此,除了'number'和'alsoNumber'值之外,不可能传递任何内容 另一个更新: 人们给了我(它有效!不幸的是,autocomplete没有): type NumericKeys={

我有一个通用函数:

function mkSorter<T extends { [key: string]: unknown }, K extends keyof T>(prop: K) {
  return (a: T, b: T) => a[prop] - b[prop];
}
因此,除了
'number'
'alsoNumber'
值之外,不可能传递任何内容

另一个更新:

人们给了我(它有效!不幸的是,autocomplete没有):

type NumericKeys={[P in keyof T]:T[P]扩展数字?P:never}[keyof T]
键入NumericFields={[P in NumericKeys]:number}
功能MK分拣机(道具:keyof N){
返回(a:T&N,b:T&N)=>a[prop]-b[prop];
}

因为只有
mkSorter
的结果对于
T
是通用的,所以您也可以将该通用参数移到内部,并使用助手类型强制
a
b
参数上的
number
属性的存在:

type WithNumber<T, K extends PropertyKey> = T & {[_ in K]: number} 

function mkSorter<K extends string>(prop: K) {
  return <T,>(a: WithNumber<T,K>, b: WithNumber<T,K>) => a[prop] - b[prop]
}

由于只有
mkSorter
的结果对于
T
是通用的,因此您还可以将该通用参数移到内部,并使用帮助器类型强制
a
b
参数上的
number
属性的存在:

type WithNumber<T, K extends PropertyKey> = T & {[_ in K]: number} 

function mkSorter<K extends string>(prop: K) {
  return <T,>(a: WithNumber<T,K>, b: WithNumber<T,K>) => a[prop] - b[prop]
}

优雅的解决方案!谢谢,船长!哇,我每次都向你学习新的东西。我将删除我的回答:乐意帮忙:-)谢谢你的回答。也许,我是模棱两可的,所以我用一个我试图实现的用法示例更新了帖子。优雅的解决方案!谢谢,船长!哇,我每次都向你学习新的东西。我将删除我的回答:乐意帮忙:-)谢谢你的回答。也许,我是模棱两可的,所以我用一个我试图实现的用法示例更新了帖子。如果
columnsype
中的
sorter
被键入
(a:T,b:T)=>number
,那么有一个解决方案不需要显式的类型参数(因此你可以编写
mkSorter('number')
,而不是
mkSorter('number'))
)。如果您仍然感兴趣,我可以更新我的答案。如果
列中的
sorter
键入
(a:T,b:T)=>number
,那么有一个解决方案不需要显式类型参数(因此您可以编写
mkSorter('number')
而不是
mkSorter('number')
)。如果你仍然感兴趣,我可以更新我的答案。
type WithNumber<T, K extends PropertyKey> = T & {[_ in K]: number} 

function mkSorter<K extends string>(prop: K) {
  return <T,>(a: WithNumber<T,K>, b: WithNumber<T,K>) => a[prop] - b[prop]
}
const sorter = mkSorter('k')
const test1 = sorter({k: 9, a: true}, {k: 9, a: false})
const test2 = sorter({k: 9, b: true}, {k: 9, b: false})