【问题标题】:Transform array of objects to a map indexed by object key将对象数组转换为由对象键索引的映射
【发布时间】:2022-01-20 21:21:00
【问题描述】:

我正在尝试将对象数组转换为地图,由typescript中的对象属性值索引4.1.5

此外,我只想要某种类型的属性(这里是string

javascript 在这里提出了一个非常相似的问题:Convert object array to hash map, indexed by an attribute value of the Object

type Foo = {
        a : string
        b : number
}

const foos: Foo[] = []
// should only propose to index by 'a'
const foos_indexed_by_a = indexArrayByKey(foos, 'a')

function indexArrayByKey<T> (array: T[], key: Extract<keyof T, string>): Map<string, T> {
        return array.reduce((map, obj) => map.set(obj[key], obj), new Map<string, T>())
}

Playground Link

目前我无法访问obj 的属性key(编译失败)

感谢您的帮助:)

【问题讨论】:

    标签: arrays typescript hashmap


    【解决方案1】:

    要根据具有字符串值的键来过滤,您不能使用Extarct 来过滤字符串(不是数字或符号)的键。你可以使用KeyOfType描述here

    type KeyOfType<T, V> = keyof {
        [P in keyof T as T[P] extends V? P: never]: any
    }
    function indexArrayByKey<T, K extends KeyOfType<T, string>> (array: T[], key: K): Map<T[K], T> {
            return array.reduce((map, obj) => map.set(obj[key], obj), new Map<T[K], T>())
    }
    

    Playground Link

    我们使用T[K] 而不是string,因为T[K] 也可能是string 的子类型,因此TS 会向string 投诉,但对于某些情况,这会很好。

    【讨论】:

    • 我认为你是对的,我的回答没有抓住重点。问题清楚地表明“由对象的属性值索引”叹息 :-)
    • 感谢您的回答在 typescript v4.5.4 中非常有效,但在我使用的 v4.1.5 中却不行。对不起,我应该指定它。你有解决办法吗?
    • @Nainpo 你可以在这里将KeyOfType 的定义替换为旧的stackoverflow.com/questions/51419176/… 其余的应该可以工作。
    • 旧兼容版本的游乐场链接:typescriptlang.org/play?ts=4.1.5#code/…
    • 感谢新定义,没关系! :)
    猜你喜欢
    • 2014-12-03
    • 1970-01-01
    • 2019-05-12
    • 1970-01-01
    • 1970-01-01
    • 2016-02-18
    • 1970-01-01
    • 1970-01-01
    • 2022-01-18
    相关资源
    最近更新 更多