TypeScript 中的函数类型函数类型签名 作为 TypeScript 的初学者,我了解到函数类型签名是 TypeS
函数类型签名
函数类型签名是 TypeScript 中描述函数入参类型与返回值类型的一种方式。它使用 :
语法进行类型标注,这样能够清晰地知道每个函数期望接收什么类型的参数,以及它将返回什么类型的值。例如:
function func(name: string): number {
return name.length;
}
函数的声明与表达式
在 JavaScript 中,可以通过函数声明或函数表达式来定义函数。TypeScript 通过类型注解增强了这些定义,能够更准确地指定函数的类型。例如:
// 函数声明
function func(name: string, age: number): string {
return `Hello, ${name}! You are ${age} years old.`;
}
// 函数表达式
const func = function(name: string, age: number): string {
return `Hello, ${name}! You are ${age} years old.`;
}
箭头函数
箭头函数是 ES6 的一个特性,在 TypeScript 中,箭头函数的类型签名与普通函数类似,但语法更简洁。
// 箭头函数的类型注解
const func = (name: string, age: number): string => {
return `Hello, ${name}! You are ${age} years old.`;
};
const message = func("lin", 18);
可以使用类型别名来为函数创建更复杂的类型注解:
type TestFunction = (name: string, age: number) => string;
const func: TestFunction = (name, age) => {
return `Hello, ${name}! You are ${age} years old.`;
};
可以使用接口来定义函数类型:
interface TestInterface {
(name: string, age: number): string;
}
const func: TestInterface = (name, age) => {
return `Hello, ${name}! You are ${age} years old.`;
};
void 类型
在 TypeScript 中,没有返回值的函数应该被标记为 void
类型。这与 JavaScript 中的 undefined
不同,它更明确表明函数不返回任何有意义的值:
// 没有返回值的函数
function func(): void { }
可选参数与 rest 参数
// 可选参数
function func1(name: string, age?: number): number {
const inputAge = age || 18;
return name.length + inputAge;
}
// rest 参数
function func(arg1: string, ...rest: number[]): number {
return arg1.length + rest.reduce((a, b) => a + b, 0);
}
函数重载
函数重载能够为同一个函数名定义多个类型签名,每个签名可以有不同的参数类型和返回值类型。能够根据传入的参数类型来决定函数的行为:
function func(foo: number, bar: true): string;
function func(foo: number, bar?: false): number;
function func(foo: number, bar?: boolean): string | number {
if (bar) {
return String(foo);
} else {
return foo * 666;
}
}
异步函数与 Generator 函数
异步函数和 Generator 函数在 TypeScript 中也有特定的类型签名。能够在处理异步操作和迭代器时保持代码的类型安全:
// 异步函数
async function asyncFunc(): Promise<void> {}
// Generator 函数
function* genFunc(): Iterable<void> {}
示例1
在函数类型中处理错误,并且使用 try-catch 结构与异步函数结合的例子。
async function fetchData(url: string): Promise<Data> {
try {
const response = await fetch(url);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
return await response.json();
} catch (error) {
throw error; // or handle the error appropriately
}
}
示例2
创建一个API请求函数,该函数可以处理不同类型的请求和响应。
首先,定义一些类型来描述请求配置和响应:
// 定义一个类型来描述API请求配置
interface ApiRequestConfig {
url: string;
method: 'GET' | 'POST' | 'PUT' | 'DELETE';
headers?: Record<string, string>;
body?: object;
}
// 定义一个泛型接口来描述API响应
interface ApiResponse<T> {
data: T;
status: number;
statusText: string;
}
接下来,创建一个泛型函数apiRequest
,它接受一个ApiRequestConfig
对象,并返回一个Promise
,该Promise
解析为定义的ApiResponse
类型的实例:
// 泛型API请求函数
async function apiRequest<T>(config: ApiRequestConfig): Promise<ApiResponse<T>> {
const response = await fetch(config.url, {
method: config.method,
headers: config.headers,
body: config.body ? JSON.stringify(config.body) : null,
});
if (!response.ok) {
throw new Error(`API request failed with status ${response.status}`);
}
const data: T = await response.json();
return {
data,
status: response.status,
statusText: response.statusText,
};
}
接下来就可以重用apiRequest
函数来处理不同类型的API调用。
例如,如果想要获取用户列表,可以这样做:
// 定义用户类型
interface User {
id: number;
name: string;
email: string;
}
// 使用apiRequest函数获取用户列表
async function fetchUsers(): Promise<ApiResponse<User[]>> {
const requestConfig: ApiRequestConfig = {
url: 'https://api.example.com/users',
method: 'GET',
};
return apiRequest<User[]>(requestConfig);
}
结论
通过学习 TypeScript 的函数类型,能更好地编写类型安全和可维护的代码。
转载自:https://juejin.cn/post/7374307181481410614