如何为支持数组或展开参数的TypeScript函数添加类型注解?
TypeScript实现支持两种调用方式的
printNums函数 这是个很典型的函数重载场景,我们可以通过TypeScript的函数重载特性完美复刻原JavaScript函数的行为,同时保证类型安全。下面是具体的实现方案:
推荐实现(避免arguments,更符合现代TS风格)
// 定义两种合法的调用签名(函数重载) function printNums(...nums: number[]): void; function printNums(nums: number[]): void; // 函数核心实现 function printNums(...args: [number[]] | number[]): void { let numArray: number[]; // 区分两种调用场景 if (args.length === 1 && Array.isArray(args[0])) { numArray = args[0]; } else { numArray = args as number[]; } // 遍历输出每个数字 numArray.forEach(num => { console.log(`Num: ${num}`); }); }
代码细节解释
函数重载签名:
- 第一个重载
printNums(...nums: number[]): void:明确了"传入任意数量的number类型参数"的调用方式(比如printNums(1,2,3))。 - 第二个重载
printNums(nums: number[]): void:明确了"传入单个number数组"的调用方式(比如printNums([1,2,3]))。
这两个重载会让TypeScript在你调用函数时,自动匹配对应的签名,提供准确的类型提示和参数检查。
- 第一个重载
实现签名逻辑:
...args: [number[]] | number[]表示参数要么是包含一个数组的元组(对应传入单个数组的情况),要么是多个number组成的数组(对应传入分散参数的情况)。- 内部通过判断参数长度和类型,统一将输入处理成
number[]类型,再执行遍历输出逻辑,保证代码的一致性。
测试调用示例
两种调用方式都能通过TypeScript的类型检查,行为和原JavaScript函数完全一致:
printNums(1, 2, 3); // 输出: // Num: 1 // Num: 2 // Num: 3 printNums([1, 2, 3]); // 输出和上面完全一致
兼容原JS的arguments写法
如果你更习惯保留原JavaScript中使用arguments的逻辑,也可以这样实现:
function printNums(...nums: number[]): void; function printNums(nums: number[]): void; function printNums(nums: number[] | number): void { let numArray: number[]; if (Array.isArray(nums)) { numArray = nums; } else { // 将arguments转换为number数组,需要类型断言确保类型安全 numArray = Array.from(arguments) as number[]; } numArray.forEach(num => { console.log(`Num: ${num}`); }); }
不过这种写法依赖arguments对象,在严格模式或现代ES模块中,arguments的使用场景已逐渐被rest参数替代,所以更推荐第一种写法。
内容的提问来源于stack exchange,提问作者Saad
相关产品推荐
相关产品推荐

