[英]Why am I keep getting TypeScript error “No overload matches this call” when using Array concat?
I've written a function to get first n
items from an array:我写了一个 function 从数组中获取前n
项目:
export const first = <T>(array: T[], n?: number): T[] => {
if (n) return array.slice(0, n)
return [].concat(array).shift()
}
Here is the link of the script to reproduce.这是要重现的脚本的链接。
The compiler returns an error编译器返回错误
error TS2769: No overload matches this call.
Overload 1 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
Argument of type 'T[]' is not assignable to parameter of type 'ConcatArray<never>'.
The types returned by 'slice(...)' are incompatible between these types.
Type 'T[]' is not assignable to type 'never[]'.
Type 'T' is not assignable to type 'never'.
Overload 2 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
Argument of type 'T[]' is not assignable to parameter of type 'ConcatArray<never>'.
return [].concat(array).shift()
When I check lib.es5.d.ts
file with VSCode, concat
accepts two overloading parameters.当我用 VSCode 检查lib.es5.d.ts
文件时, concat
接受两个重载参数。
concat(...items: ConcatArray<T>[]): T[];
concat(...items: (T | ConcatArray<T>)[]): T[];
By seeing the second type of call, I've tried to change the first parameter of first
function from array: T[]
to array: (T | ConcatArray<T>)[]
but then it returns error,通过查看第二种类型的调用,我尝试将第first
function 的第一个参数从array: T[]
更改为array: (T | ConcatArray<T>)[]
但随后它返回错误,
Overload 2 of 2, '(...items: ConcatArray<never>[]): never[]', gave the following error.
Argument of type '(T | ConcatArray<T>)[]' is not assignable to parameter of type 'ConcatArray<never>'
What should I do to fix those errors?我应该怎么做才能修复这些错误? I'm new to TypeScript so pardon me if this is a dumb question.我是 TypeScript 的新手,如果这是一个愚蠢的问题,请原谅我。
In this github issue you can see why the array have a never type ,the principal response is:在这个 github 问题中,您可以看到为什么数组有 never 类型,主要响应是:
This is caused by the combination of strict and noImplicitAny: false.这是由 strict 和 noImplicitAny: false 的组合引起的。 In general we expect that if strict is on, noImplicitAny is also on;一般来说,我们希望如果 strict 开启,则 noImplicitAny 也开启; this particular set of settings will expose some odd behavior.这组特定的设置会暴露一些奇怪的行为。 If you had both on, you'd see an error about the [] being implicitly any[];如果两者都打开,您会看到关于 [] 隐含为 any[]; 的错误。 if both were off;如果两者都关闭; we'd use control flow analysis and treat the array as a number[] after the push(1);.我们将使用控制流分析并将数组视为 push(1); 之后的数字[]。
The particular combination of settings means that we don't allow ourselves to use control flow analysis or allow the array to be implicitly any[], so never[] is the only remaining allowable option.设置的特定组合意味着我们不允许自己使用控制流分析或允许数组隐含为 any[],因此 never[] 是唯一剩下的允许选项。
I'd recommend turning off strict if you're not going to have noImplicitAny on.如果您不打算启用 noImplicitAny,我建议您关闭 strict。
respect to how to fix your problem, you can use any of the two approaches I write in this TS playground , I recommend you the second because there you will take in account the two possible values returned by the function, in the first you just cheat TS with the type assertion to return T[], but probably the type will be undefined when the array doesn't have a value.关于如何解决您的问题,您可以使用我在此 TS 操场上编写的两种方法中的任何一种,我建议您使用第二种方法,因为您将考虑 function 返回的两个可能值,首先您只是作弊TS 带有返回 T[] 的类型断言,但是当数组没有值时,类型可能是未定义的。
const second = <T>(array: T[], n?: number): (T | undefined)[] => {
if (n) return array.slice(0, 2)
return [array.shift()]
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.