1.TS内置高级类型Partial&Pick&Required&Readonly
1.1、Partial
Partial 可以快速把某个接口类型中定义的所有属性变成可选的
interface ApiKey {
id: number;
name: string;
}
const dataType1: ApiKey = {
id: 1,
name: 'static'
}
const dataType2: ApiKey = {
name: 'json'
}
这段代码会在编译报错:
因为dataType2
的类型是ApiKey,ApiKey中id
和name
都是必选的,这导致编译报错。假如ApiKey
中的参数是可选的,那么这个问题就会不复存在,而Partial
的作用就在于此,它可以帮助我们把ApiKey
中的所有属性都变成可选的
我们用Partial
来重写一下这个栗子:
const dataType2: Partial<ApiKey> = {
name: 'json'
}
这样就不会报错啦!
1-2、Pick
可以
选择
一个原来的接口中一部分的属性定义interface People {
name: string
age: number
}
type somePeople = Pick<People,'name'>
let onlyName:somePeople = {
name:"112"
}
选择了接口中的name属性,那么该属性就必须含有
1-3、Required
和
Partial
刚好相反,将一个定义中的属性全部变成必选参数
// 必选参数
interface People1 {
name?: string;
age?: number;
}
// 类型 "{ name: string; }" 中缺少属性 "age",但类型 "Required<People>" 中需要该属性
const person2: Required<People1> = {
name:"11"
}
1-4、Readonly
只读,让一个定义中的所有属性都变成
只读参数
interface People3 {
name: string
age: number,
dog:{
name:string
age:number
}
}
const xiaoling: Readonly<People3> = {
name: '小凌', // 只读
age: 18, // 只读
dog:{
age:1,
name:'大黄'
}
}
// 但是是浅层的
xiaoling.name = '大凌' // 无法分配到 "name" ,因为它是只读属性。
xiaoling.dog.age = 2 // 可以
2.联合类型(UnionType)
首先是联合类型的介绍,也是一切的起源
let a: string | number | boolean = '123' // 变量a的类型既可以是string,
a = 123 // 也可以是number
a = true // 也可以是boolean
3.keyof
将一个类型的属性名全部提取出来当做
联合类型
// key of 使用
interface People5 {
name: string;
age: number;
}
// keyof 取 interface 的键
// type keys = "name" | "age"
type keys = keyof People5;
// 假设有一个 object 如下所示,
// 我们需要使用 typescript 实现一个 get 函数来获取它的属性值
const xiaozhang:People5 = {
name: '小张',
age: 12
}
function get<T extends object, K extends keyof T>(o: T, name: K): T[K] {
return o[name]
}
console.log(get(xiaozhang,'age')) // 12
console.log(get(xiaozhang,'name')) // 小张
// error 类型“"address"”的参数不能赋给类型“keyof People”的参数。
console.log(get(xiaozhang,'address'))
keyof
与 Object.keys
略有相似,只不过 keyof
取 interface
的键
4.映射(Record)
Record用于属性映射
搭配联合类型
type RequestMethods = 'GET'|'POST'| 'DELETE'
type MethodsAny = Record<RequestMethods, any>
let mothod1:MethodsAny = {
GET:"1",
POST:'1',
DELETE:'1'
}
let mothod2:MethodsAny = {
GET:"1",
POST:'1',
DELETE:'1', // 缺少,会报错,因为它为必须存在的
PUT:'111' // error “PUT”不在类型“MethodsAny”中
}
搭配接口使用
interface PersonModel {
name:string,
age:number
}
// [x: string]: PersonModel;
type student = Record<string, PersonModel>
let students:student = {
student1:{
name:'小凌',
age:18
},
student2:{
name:'小李',
age:19
}
}
5.Exclude(排除)
ts中可以排除 联合类型 中一部分的内容
注意:Exclude用来操作联合类型
的
type havTypes = 'name' | 'age' | 'sex'
type someTypes = Exclude<havTypes,'sex'>
const myTypes1:someTypes = 'name' // 可以
const myTypes2:someTypes = 'sex' // 错误 不能将类型“"sex"”分配给类型“someTypes”
6.Omit (省略)
ts中就是将接口或者类型的键值对删除一部分
// 省略
interface People {
name: string;
age: number;
}
type somePeople = Omit<People,'name'>
/**
type somePeople = {
age: number;
}
*/
7.ReadonlyArray(只读数组)
创建一个数组,数组中的索引不允许被修改
我们知道当我们使用const
创建对象或者数组时,其实是可以修改其内部属性的,但是有的时候我们可能不需要其内部能够被修改,这时候我们就需要用ReadonlyArray
了
实现的方式有两种:
// 方法1:通过类型断言的方式
const arr = ['小伟','小铁','小涵','小凌'] as const
arr[3] = '帅哥'; // 报错 无法分配到 "3" ,因为它是只读属性
// 方法2:使用ReadonlyArray
const arr2 : ReadonlyArray<string> = ['木兰','盾山','凯','百里守约']
arr2[3] = '百里玄策' // 报错 类型“readonly string[]”中的索引签名仅允许读取
你是不是就想知道
as const
和ReadonlyArray
这两者的区别在哪里?区别在于
as const
是深层次的,尽管数组内放的对象,对象内部数据也是不能被修改的。ReadonlyArray
则是‘浅层’
的const:
ReadonlyArray:
可以看到修改ReadonlyArray
数组内的第二层其实是可以的
白日不到处,青春恰自来,苔花如米小,也学牡丹开。