【问题标题】:How can I define Array.reduce method in Typescript?如何在 Typescript 中定义 Array.reduce 方法?
【发布时间】:2021-12-09 13:29:34
【问题描述】:

我对 TypeScript 中的 reduce 方法有疑问:

const items = {a: 10, b:20, c: 30}
const itemsTotal = Object.keys(items).reduce((accumulator: number, key: keyof typeof items ) => {
    return accumulator + items[key]
  }, 0)

我不断收到 Typescript 错误:

'(accumulator: number, key: "a" | "b" | "c") => number' 类型的参数不能分配给 '(previousValue: string, currentValue: string, currentIndex: number , 数组:字符串[]) => 字符串'。

Types of parameters 'accumulator' and 'previousValue' are incompatible.***

看来我需要定义reduce方法的类型,但是怎么做呢?

【问题讨论】:

    标签: typescript


    【解决方案1】:

    Object.keys 返回一个string[],所以你不能应用一个需要keyof typeof items 的reducer 函数。

    你可以使用类型断言,因为你知道它是有效的:

    const items = {a: 10, b:20, c: 30};
    const itemsTotal = Object.keys(items).reduce((accumulator, key) => {
        return accumulator + items[key as keyof typeof items];
    }, 0);
    

    Playground

    ...但是你不需要密钥,只需使用Object.values

    const items = {a: 10, b:20, c: 30};
    const itemsTotal = Object.values(items).reduce((accumulator, value) => {
        return accumulator + value;
    }, 0);
    

    Playground

    (但坦率地说,我只会使用a simple loop。)

    【讨论】:

    • 谢谢 T.J.你的两个答案都解决了我的问题。给你荣誉
    【解决方案2】:

    不是最干净的解决方案,但您可以使用这个 sn-p:

    const items = { a: 10, b: 20, c: 30 }
    const itemsTotal = Object.keys(items).reduce((accumulator, key) => {
        return accumulator + items[key as keyof typeof items]
    }, 0)
    

    关键是将key转换为keyof typeof items

    【讨论】:

    • 很好的答案@Drag13,它解决了我的问题。
    【解决方案3】:

    将您的项目定义为Recordstringnumberreduce 方法将清楚该项目是number

    const items: Record<string, number> = {a: 10, b: 20, c: 30}
    
    const itemsTotal = Object.keys(items).reduce((accumulator: number, key: string) => {
        return accumulator + items[key];
    }, 0)
    

    您也可以跳过reduce 正文中的大括号。

    Object.keys(items).reduce((acc: number, key: string) => acc + items[key], 0)
    

    此外,您可以跳过 reduce 中的类型名称,因为您的 items 已经在 Record 中定义为数字。

    Object.keys(items).reduce((acc, key) => acc + items[key], 0)
    

    编辑

    您可以跳过累加器初始化。 reduce 在这种情况下从第一项开始。

    Object.values(items).reduce( (acc, item) => acc + item )
    

    最快的解决方案是使用for of,因为没有函数调用:

    let sum = 0
    for (const item of Object.values(items)) {
       sum += item;
    }
    

    【讨论】:

    • 谢谢米罗斯拉夫。
    • @Manzana,定义你的对象总是一个好主意。使用 Record&lt;string, number&gt; 定义键和值。
    猜你喜欢
    • 1970-01-01
    • 2018-05-06
    • 1970-01-01
    • 1970-01-01
    • 2019-07-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多