TypeScript 如何做回调类型

写代码时,我们常常需要把一段“要做的事”打包传给别人,等对方准备好后再执行——这种“延后执行的函数”就是回调。但如果回调传错格式,比如要求传数组结果却给了字符串,代码很容易炸锅。TypeScript 能帮我们提前堵住这类坑,核心就是给回调加上“类型约束”。

先搞懂最基础的回调类型

假设我们要做一个“水果采购”的小功能:先去市场买水果,等买完了,再用回调告诉老板“买完啦,接下来要算账”。用普通 JavaScript 写的话,函数很灵活,但没人能保证传的回调是对的:

TypeScript 如何做回调类型

`javascript

// 普通JS写法,容易出错

function buyFruit(fruit, callback) {

console.log(买了${fruit});

callback(); // 老板要求的是“买完”,但传回调的人可能写错

}

// 没问题的情况

buyFruit("草莓", () => console.log("开始算账"));

// 容易错的情况:传了数字,完全不是函数

buyFruit("香蕉", 123);

`

换成 TypeScript,只要给回调加个类型注解,就能提前拦住错的:

`typescript

// 给callback加了“必须是无参数、无返回值的函数”的约束

function buyFruit(fruit: string, callback: () => void) {

console.log(买了${fruit});

callback();

}

// 正确:传了符合要求的函数

buyFruit("草莓", () => console.log("开始算账"));

// 错误:TS会直接标红,说“你传的123不是函数”

buyFruit("香蕉", 123);

`

这就是回调类型的基础作用:明确“回调该长什么样”,避免传错。

带参数的回调怎么写?

实际工作里,回调经常要拿前面函数的结果用。比如买完水果要把买了多少斤告诉回调,这时候就得给回调加“接收参数”的类型。

比如我们要做个“点外卖”的功能:下单后,回调要拿到“外卖费”来显示总价格。这时候回调需要接收一个数字参数,TypeScript 可以这么写:

`typescript

// callback要接收一个number类型的参数,返回void

function orderTakeout(food: string, callback: (deliveryFee: number) => void) {

console.log(下单了${food});

const fee = 5; // 假设外卖费固定5元

callback(fee); // 把外卖费传给回调

}

// 正确:回调接收参数,TS自动知道参数是number

orderTakeout("披萨", (fee) => console.log(总价格:100 + ${fee} = 105元));

// 错误:回调没传参数,TS会提示“缺少参数”

orderTakeout("汉堡", (fee) => console.log(总价格:100元));

`

这里的 (deliveryFee: number) => void 就是“带数字参数的无返回函数”,正好对应老板要的“拿到外卖费再算总价”的需求。

回调返回值也能加类型

有时候回调会返回结果,比如我们要做“批量打印名片”的功能:打印完每张名片,回调要返回“是否打印成功”,最后把所有结果收集起来。这时候需要给回调的返回值加类型。

TypeScript 里可以这么写:

`typescript

// callback接收名片名字,返回boolean(是否成功),最后collectResults会收集所有结果

function printCards(names: string[], callback: (name: string) => boolean) {

const results: boolean[] = [];

for (const name of names) {

const success = callback(name);

results.push(success);

}

return results;

}

// 正确:回调返回boolean,符合要求

const results = printCards(["张三", "李四"], (name) => {

console.log(打印${name}的名片);

return name.length > 2; // 名字超过2字才打印成功

});

console.log(results); // [true, true]

`

要是回调返回了字符串,TS会直接标红,说“返回类型不符合要求”,避免后续用结果时出错。

用类型别名简化复杂回调

如果回调的类型太复杂,比如要同时接收多个参数,还带返回值,反复写会很麻烦。这时候可以用 TypeScript 的类型别名,把回调的类型存成一个变量,方便复用。

比如我们要做“不同店铺的优惠计算”,每个店铺的回调都要接收“原价”和“会员等级”,返回“优惠后的价格”:

`typescript

// 把回调的类型存成PriceCalculator,方便复用

type PriceCalculator = (originalPrice: number, memberLevel: string) => number;

function calculateDiscount(price: number, calculator: PriceCalculator) {

const memberLevel = "黄金"; // 假设当前会员等级

return calculator(price, memberLevel);

}

// 用类型别名传回调,清晰不容易错

const goldDiscount: PriceCalculator = (price, level) => {

return level === "黄金" ? price * 0.8 : price;

};

console.log(calculateDiscount(100, goldDiscount)); // 输出80

`

这样不管要加多少种优惠计算方式,只要 PriceCalculator 类型不变,就不会传错回调格式。

简单来说,TypeScript 做回调类型,就是给“要传给别人的函数”定好规矩,从根源上减少代码出错,尤其适合多人协作的项目,哪怕新手写回调,也能通过类型提示快速知道该怎么写。

上一篇 Swift语言核心特性解析:从基础语法到实际开发应用的全面科普