深入对象
索引签名(Index Signature)
我们已经很熟悉了
type Hash = {
[key: stirng]: unknown;
length: number;
}
type List {
[key: number]: unknown;
length: number;
}
映射类型(Mapped Type)
多用于泛型
type List {
[key in string]: unknown;
}
type List {
[key in number]: unknown;
}
可选类型
对象的某个属性可用可不用
interface Person {
name: string;
age: number;
onChange?: () => void;
}
const p: Person = {
name: 'hi',
age: 18
}
只读类型
表示只读,不能写
interface Person {
name: string;
age: number;
readonly id: number;
}
const p: Person = {
name: 'hi',
age: 18,
id: 1,
}
p.name = 'new name'
p.id = 2 // TODO: 报错,Cannot assign to 'id' because it is a read-only property.ts
深入函数
对象的语法全都适用于函数,函数也可以用对象来声明
type F = {
(a: number, b: number) => void;
count: number;
}
// 普通声明
type F1 = (a: number, b: number) => void
声明方式
JS 函数的三种声明方式
function f1(a) {
/* ... */
}
const f2 = function(a) {
/* ... */
}
const f3 = () => {
/* ... */
}
那么相对应 TS 的
function f1(a: number): number {
/* ... */
}
const f2 = function (a: number): number {
/* ... */
}
const f3 = (a: number): number => {
/* ... */
}
// 也可以把类型提取出来,写在等号左边,比较推荐
type F2 = (a: number) => number
const f2: F2 = function (a) {
/* ... */
}
可选参数
function addEventListener(eventType: string, fn: unknown, useCapture?: boolean) { // TODO: 加上问号就好了
/* ... */
}
addEventListener('click', () => 1)
参数默认值
实际情况我们会更倾向于使用默认值
// 和上面的代码等价
function addEventListener(eventType: string, fn: unknown, useCapture=false) {
/* ... */
}
addEventListener('click', () => 1)
返回值也是函数
type Add = (x: number) => (y: number) => number
const add: Add = a => b => a + b