如何让TypeScript的Process类根据传入函数参数推断参数类型
让Process类的parameters参数与fn参数类型匹配的TypeScript实现方案
要实现传入Process构造函数的parameters参数类型与fn的参数类型严格匹配,你需要利用TypeScript的泛型来捕获函数的参数类型,替代原来的any和Function类型(这两种类型会丢失类型检查能力)。
实现代码
// 补充Message类型示例(若你已有定义可忽略) type Message = { content: string }; class Process<T extends any[]> { readonly fn: (...args: T) => any; readonly parameters: T extends [infer U] ? U | T : T; nextMessage: Message | null = null; constructor(fn: (...args: T) => any, parameters: T extends [infer U] ? U | T : T) { this.fn = fn; // 将单个参数转为元组,统一内部存储格式 this.parameters = (Array.isArray(parameters) ? parameters : [parameters]) as T; } }
验证示例
function doTask(task: string){ console.log(`doing ${task}`); } // ✅ 正确:传入匹配的字符串参数 const validProcess1 = new Process(doTask, "Something"); // ✅ 正确:也支持传入元组形式的参数 const validProcess2 = new Process(doTask, ["Something"]); // ❌ 错误:传入数字类型,TypeScript会抛出类型不匹配的错误 const invalidProcess = new Process(doTask, 123);
多参数函数的适配
这个方案同样支持多参数的函数:
function calculateSum(a: number, b: number): number { return a + b; } // ✅ 正确:传入匹配类型的参数元组 const sumProcess = new Process(calculateSum, [10, 20]); // ❌ 错误:参数类型不匹配,TypeScript报错 const invalidSumProcess = new Process(calculateSum, [10, "20"]);
原理说明
- 泛型
T extends any[]用于捕获传入函数fn的参数元组类型,比如doTask的参数元组是[string],calculateSum的是[number, number]。 - 条件类型
T extends [infer U] ? U | T : T实现了单参数场景的灵活传参:当函数只有一个参数时,既可以传入单个值,也可以传入元组;多参数时必须传入元组。 - 构造函数内部通过
Array.isArray判断,将单个值转为元组,保证内部存储的参数格式统一,方便后续调用fn时展开参数。
内容的提问来源于stack exchange,提问作者alumen-
相关产品推荐
相关产品推荐

