在Array.reduce中使用某些初始值时,TypeScript报告错误

在Array.reduce中使用某些初始值时,TypeScript报告错误,typescript,Typescript,在Array.reduce中使用某些初始值时,TypeScript在此报告一个奇怪的错误 类型为“number”的错误参数不可分配给类型为“never”的参数在以下示例的第2行中显示为c: const foo = [1, 2, 3].reduce((p, c) => { p.bar.push(c); return p; }, {bar: []}); document.write(`foo=${JSON.stringify(foo)}`); 如果启用了stricnullc

在Array.reduce中使用某些初始值时,TypeScript在此报告一个奇怪的错误

类型为“number”的错误
参数不可分配给类型为“never”的参数
在以下示例的第2行中显示为
c

const foo = [1, 2, 3].reduce((p, c) => {
    p.bar.push(c);
    return p;
}, {bar: []});

document.write(`foo=${JSON.stringify(foo)}`);

如果启用了
stricnullchecks
,并且原因充分,则会发生此错误。
Array.reduce
的初始值为
{bar:[]}
,无法解析为安全类型。数组是否为任何[]或编号[]?因此,TypeScript假定它是
从不[]
,因为它无法从lambda中的用法推断数组的类型(它只能反过来工作)

顺便说一句,如果没有
stricnullchecks
,数组的类型为
undefined[]
,但该标志基本上将
undefined
的所有出现替换为一个类型为
never
,这会导致您的示例在表单
const foo=[]的赋值和赋值之后失败的类型为
从不[]
,具有严格的设置

为了解决此问题,您必须将初始值设置为
{bar:[]as number[]}
,以显式键入数组并使其工作:

const foo = [1, 2, 3].reduce((p, c) => {
    p.bar.push(c);
    return p;
}, {bar: [] as number[]});

document.write(`foo=${JSON.stringify(foo)}`);

谢谢你的解释,但我还是很困惑。根据您的解释,这都是关于非类型化数组的,但是为什么
[1,2,3].reduce((p,c)=>{p.push(c);返回p;},[])然后无误工作?@doberkofler启用
strictNullChecks
时它也不工作。正确。我的错误。所以这个例子可以简化为下面的例子
constfoo={foo:[]};foo.foo.push(1)。但是为什么我可以使用
constbar=[];推杆(1)
没有错误?同样地,
条形图
属于
never[]
类型,在启用了
strictNullChecks
的情况下,它不会为我编译。@doberkofler标志所做的是替换类型
未定义的
的出现,例如数组
未定义的[]
。它将所有出现的
未定义
替换为
从不
,以导致编译时错误,除非您显式键入它们。空数组累加器将自动键入为
从不
。另一种可行的方法是在第一行中键入累加器
p