Types
TIP
JS 是动态类型,在运行时才能够决定数据的类型;TS 是静态类型,在开发时就需要明确数据的类型。
核心数据类型
number
string
boolean
object
TS 可以基于我们写的代码进行类型推断:
也可以主动去声明类型:
ts
const person: {
name: string;
age: number;
} = {
name: 'jiaqi',
age: 25,
};
Array
ts
const person: {
name: string;
age: number;
hobbies: string[];
} = {
name: 'jiaqi',
age: 25,
hobbies: ['sports', 'games'],
};
在这里能体会到 TS 的一个好处就是当明确了一个变量的类型的时候,IDE 就可以根据类型去推断相应的方法:
上图中就很好地根据 hobby
是字符串而推荐了相应的 toUpperCase()
方法。
Tuple
元组
ts
const person: {
name: string;
age: number;
hobbies: string[];
role: [number, string];
} = {
name: 'jiaqi',
age: 25,
hobbies: ['sports', 'games'],
role: [2, 'author'],
};
通过这种方式声明的变量就表示 role
的第一个元素必须是 number
第二个元素必须是 string
,这是不可变的。
Enum
可枚举
ts
enum Role {ADMIN, READ_ONLY, AUTHOR}
const person = {
name: 'jiaqi',
age: 25,
hobbies: ['sports', 'games'],
role: Role.ADMIN,
};
声明这种可枚举属性会自动为其中每个元素分配一个数字标识符,在 JS 中的实现方式如下:
js
var Role;
(function (Role) {
Role[Role["ADMIN"] = 0] = "ADMIN";
Role[Role["READ_ONLY"] = 1] = "READ_ONLY";
Role[Role["AUTHOR"] = 2] = "AUTHOR";
})(Role || (Role = {}));
any
Union 和 Literal 类型
Union Type
联合类型:
ts
// 如果传入的是字符串,就直接组合;如果传入的是数字,就相加
function combine(input1: number | string, input2: number | string) {
let res;
if (typeof input1 === 'number' && typeof input2 === 'number') {
res = input1 + input2;
} else {
res = input1.toString() + ' ' + input2.toString();
}
return res;
}
Literal Type
一个提前规定好的固定值,赋值时只能从这固定值中选择。
ts
function combine(
input1: number | string,
input2: number | string,
resultConversion: 'as-number' | 'as-text'
) {
let res;
if (
(typeof input1 === 'number' && typeof input2 === 'number') ||
resultConversion === 'as-number'
) {
res = +input1 + +input2;
} else {
res = input1.toString() + ' ' + input2.toString();
}
return res;
}
const combinedAges = combine(18, 25, 'as-number');
const combinedNames = combine('jiang', 'jiaqi', 'as-text');
Alias 类型别名
ts
type Combinable = number | string;
ts
type ConversionDescriptor = 'as-number' | 'as-text';
函数返回值类型
手动声明返回值的类型:
当返回值的类型与声明的类型不同的时候,就会报错。
当没有明确地返回一个值的时候,默认返回值为 void
:
函数类型与回调函数
如上图所示,当我们将 combineValues
设置为 Function
时,我们就无法将其他类型的量赋值给它。
TIP
F 大写。
如果我们想要更加明确这个 Function
的形式,此时就要函数类型出马了。
ts
function add(n1: number, n2: number) {
return n1 + n2;
}
let combineValues: (a: number, b: number) => number;
combineValues = add;
console.log(combineValues(8, 8));
这里定义了参数个数、参数类型与返回值类型。
当回调函数作为参数的时候,定义回调函数的函数类型:
ts
function addAndHandle(n1: number, n2: number, cb: (a: number) => void) {
const result = n1 + n2;
cb(result);
}
addAndHandle(10, 20, (res) => {
console.log(res); // 30
});
unknown 和 never
上面的代码中由于无法确定 userInput
的类型,所以不允许直接赋值给 string
类型的变量。如果想要赋值,需要进行类型判断。
ts
let userInput: unknown;
let userName: string;
userInput = 'jiaqi';
if (typeof userInput === 'string') {
userName = userInput;
}
这里也体现了 unknown
与 any
的不同。
返回 never
的函数:
ts
function generateError(message: string, code: number) {
throw { message: message, errorCode: code };
}
const res = generateError('An error occurred!', 500);
console.log(res); // 不打印 undefined 这是由于该函数返回 never 而不是 void