文章目录

  • TypeScript高级类型
    • class类
      • 构造函数
      • 实例方法
      • 类的继承
      • 类成员的可见性
    • 类型兼容性
      • 接口之间的兼容性
      • 函数之间的兼容性
        • 参数个数
        • 参数类型
        • 返回值类型
    • 交叉类型
    • 泛型
      • 泛型约束
      • 接口中的泛型
      • 泛型类
      • 泛型工具类型
        • Partial
        • Readonly
        • Pick
        • Record
    • 索引签名类型
    • 映射类型
      • 索引查询类型

TypeScript高级类型

class类

TypeScript全面支持ES2015中引入的class关键字,并未其添加了类型注解和其他语法

class Persion{age: number,gender = '男'
}const p = new Persion()
  1. 根据TS中的类型推论,可以知道Persion类的实例对象p的类型是Persion
  2. Ts中的class,不仅提供了class语法功能,也作为一种类型存在
  3. 声明成员age,类型number(没有初始值)
  4. 声明gender,并设置初始值,此时,可以省略类型注解(TS有类型推断机制)

构造函数

class Person{age: numbergender: string// 构造函数不需要返回值类型constructor(age: number , gender: string){this.age = agethis.gender = gender}
}

实例方法

class Point {y = 10x = 10scale(n: number): void {this.x *= nthis.y * = n}
}

类的继承

说明: JS中只有extends,而implements是TS提供的
extends继承父类 implements实现接口

class Animal {move(){console.log('Moving along!')}
}
class Dog extends Animal{bark(){console.log('汪!')}
}
const dog = new Dog()
  1. 通过extends关键字实现继承
  2. 子类Dog继承父类Anmial,则Dog的实例对象dog就同时具有了父类Animal和子类Dog的所有属性和方法

类成员的可见性

可以使用TS来控制class的方法或属性对于class外的代码是否可见
可见性修饰符包括:

  1. public(公有的)
  2. protected(受保护的)仅在声明所在类和子类中(非实例对象)
  3. private(私有的)只在当前类中可见,对实例对象一级子类也是不可见的
  4. readonly(只读修饰符)表示只读属性,用来防止在构造函数之外对属性进行赋值,接口或者{}表示的对象类型也可以使用readonly
class Animal{public move(){console.log('Moving along!')}
}

提示: 默认的修饰符是public可以省略不写

类型兼容性

let arr = ['a','b','c']
arr.forEach(item => {})

两种类型系统:

  1. Stuctural Type System(结构化类型系统)
  2. Nominal Type System(标明类型系统)

TS采用的是结构化类型系统,也叫做duck typing(鸭子类型),类型检查关注的是值所具有的形状,也就是说,在结构类型系统中,如果两个对象具有相同的形状,则认为他们属于同一类型

class Ponit { x: number; y: number }
class Point2D { x: number; y: number }
const p: Point = new Point2D()
  1. Ponit和Point2D是两个名称不同的类
  2. 变量p的类型被显示标注为Point类型,但是,它的值却是Point2D的实例,并且没有类型错误
  3. 因为TS是结构化类型系统,只检查Point和Ponit2D的结构是否相同(相同,都具有x和y两个属性,属性类型也相同)
  4. 但是,如果Nominal Type System中(比如,C#,Java等),他们是不同的类,类型无法兼容
  5. 成员多的类可以赋值给成员少的类

接口之间的兼容性

接口之间的兼容性,类似于class,并且class和interface之间也可以兼容

interface Point { x: number , y: number }
interface Point2D { x: number , y: number }
let p1: Point
let p2: Point2D = p1

函数之间的兼容性

参数个数

参数多的兼容参数少的(参数少的可以赋值给多的)

type F1 = (a: number) => void
type F2 = (a: number, b: number) => void
let f1: F1
Let f2: F2 = f1

参数类型

相同位置的参数类型要相同(原始类型)或兼容(对象类型)

type F1 = (a: number) => string
type F2 = (a: number) => string
let f1: F1
let f2: F2 = f1

函数类型F2兼容函数类型F1,因为F1和F2的第一个参数类型相同

返回值类型

只用关注返回值类型本身

type F5 = () => string
type F6 = () => string
let f5: F5
let f6: F6 = f5
  1. 如果返回值类型是原始类型,此时两个类型要相同
  2. 如果返回值类型是对象类型,此时成员的可以赋值给成员少的

交叉类型

功能类似于接口击沉,用于组合多个类型为一个类型(常用于对象类类型)

interface Person { name: string }
interface Contact { phone: string }
type PersonDetail = Person & Contact
let obj: PersonDetail = {name: 'jack',phoneL: '133...'
}

使用交叉类型后,新的类型PersonDDetail就同时具备了Person和Contact的所有属性类型

泛型

  • 泛型是可以在保证类型安全前提下,让函数等于多种类型一起工作,从而实现复用,常用于: 函数接口class
  • 泛型在保证类型安全(不丢失类型信息)的同时,可以让函数等与多种不同类型一起工作,灵活复用
function id<T>(value: T): T { return value }//1. 在函数名称后面添加<>,尖括号中添加类型变量
//2. 类型变量T,是一种特殊类型的变量,它处理类型而不是值
//3. 该类型变量相当于一个类型容器,能够捕获用户提供的类型(具体是什么类型由用户调用该函数时指定)
//4. 因为T时类型,因此可以将其作为函数参数和返回值的类型,表示参数和返回值具有相同的类型
//5. 类型变量T,可以时任意合法变量名称

泛型约束

  • 默认情况下,泛型函数的类型变量T可以代表多个类型,这导致无法访问任何属性
  • Type可以代表任意类型,无法保证一定窜在length属性,比如number类型就没有length,此时,就需要为泛型添加约束来收缩类型
  • 添加泛型约束方式
  1. 指定要添加具体的类型
function id<T>(value: T[]): T{return value
}
  1. 添加约束
interface ILength { length: number }
function id<T extends ILength>(value: T): T{console.log(value.length)return value
}//1. 创建约束的接口ILength,该接口要求提供length属性
//2. 通过extends关键字使用该接口,为泛型(类型变量)添加约束
//3. 该约束表示: 传入的类型必须具有Length属性

泛型的类型变量可以有多个,并且类型变量之间还可以约束

function getProp<T,k extends keyof T>(obj: T,key: key){return obj[key]
}
let person = { name: 'jack' , age: 18 }
getProp(person,'name')//1. 添加第二个类型变量k,两个类型之间使用,分隔
//2. keyof关键字接收一个对象类型,生成其键名称(可能时字符串或者数字)的联合类型
//3. 本例中keyof T实际上获取的是persion对象所有键的联合类型,也就是: `'name' | 'age'`
//4. 类型变量K受T约束,可以理解为: K只能是T所有键中任意一个,或者只能访问对象中存在的属性。

接口中的泛型

接口中也可以使用泛型,增加其灵活性,增强复用性

interface IdFunc<T>{id: (value: T) => Tids: () => T[]
}
  1. 在接口名称的后面添加<类型变量>,那么,这个接口就变成了泛型接口
  2. 接口的类型变量,对接口中所有其他成员可见,也就是接口中所有成员可以使用类型变量
  3. 使用泛型接口时需要显式指定具体的类型
  4. 此时,id方法的参数和返回值类型都是number; ids方法的返回值类型时number[]

泛型类

class也可以配合泛型来使用

class GenericNumber<NumType>{defaultValue: NumTypeadd: (x: NumType,y: NumType) => NumType
}

泛型工具类型

TS内置了一些常用的工具类型,来简化TS中的一些常见操作,他们都是基于泛型实现的。

Partial

用来构建一个类型,将T的所有属性设置为可选

interface Props{id: stringchildren: number[]
}
// 构造出来的新类型PartialProps结构和Props相同,但是所有属性都变成可选属性
type PartialProps = Partial<Props>

Readonly

用来构造一个类型,将T的所有属性都设置为readonly(只读)

interface Props{id: stringchildren: number[]
}
//属性都变成刻度属性,不能赋值
type ReadonlyProps = Readonly<Props>

Pick

Pick<T,K>从T中选择一组属性来构造新类型

interface Props{id: stringtitle: stringchildren: number[]
}//1. Pick工具类型有两个类型变量: 1. 表示选择谁的属性 2. 表示选择哪几个属性
//2. 其中第二个类型变量,如果只选择一个则之传入该属性名即可
//3. 第二个类性变量传入的属性只能是第一个类型变量中存在的属性
//4. 构造出来的新类型PickProps,只有id和title两个属性类型
type PickProps = Pick<Props,'id' | 'title'>

Record

Record<K,T>构建一个对象类型,属性键为K,属性的类型为T

type RecordObj = Record<'a'|'b'|'c',string[]>//1. Record工具类型有两个类型变量: 1. 表示对象有哪些属性  2. 表示对象属性的类型
//2. 构建的新对象类型RecordObj表示: 这个对象有三个属性分别为a/b/c,属性值的类型都是string[]
let obj: RecordObj = {a: ['1'],b: ['2'],c: ['3']
}

索引签名类型

无法确定对象中有哪些属性(或者说对象中可以出现任意多个属性),此时,就用到索引签名类型

interface AnyObje{[key: string]: number
}
  1. 使用[key: string]来约束该接口中允许出现的属性名称。表示只要string类型的 属性名称,都可以出现在对象中
  2. 对象obj中就可以出现任意多个属性
  3. key只是一个占位符,可以换成任意合法的变量名称
  4. 隐藏的前置知识:JS中对象({})的键是string类型的

映射类型

基于就类型创建新类型(对象类型)

type PropKeys = 'x' | 'y' | 'z'
// type Type1 = { x: number; y: number; z: number }
type Type2 = { [Key in PropKyes]: number }
  1. 映射类型是基于索引签名类型的,所以,该语法类似于索引签名类型,也使用了[]。
  2. Key in PropKeys 表示key可以是PropKeys联合类型中的任意一个,类似于forin(let k in obj)
  3. 使用映射类型创建的新对象类型Type2类型和Type1类型结构完全相同
    注意: 映射类型只能在类型别名中使用,不能在接口中使用

映射类型除了根据联合类型创建新类型外,还可以根据对象类型来创建

type Props = { a: number; b: string; c: boolean }
type Type3 = { [ key in keyof Props]: number }
  1. 首先,先执行keyof Props获取到对象类型Props中所有键的联合类型,'a'|'b'|'c'
  2. 然后,key in…就表示key可以是Props中所有的键名称中的任意一个

索引查询类型

T[P]语法,在TS中叫做索引查询类型,用来查询属性的类型

type Props = { a: number; b: string; c: boolean }
type TypeA = number
type TypeA = Props['a']

Props[‘a’]表示查询类型Props中属性’a’对应的类型number所以,TypeA的类型为number
注意: [] 中的属性必须存在于被查询类型中,否则就会报错

同时查询多个索引类型

type Props = { a: number ; b: string; c: boolean }
type TypeA = Props['a' | 'b']
//使用字符串字面量的联合类型,获取a和b的对应的类型,结果为: string|number
type TypeA = Props[keyof Props]
//使用keyof操作符取Props中所有键对用的类型,结果为: string | number | boolean
类型Props中属性'a'对应的类型number所以,TypeA的类型为number
`注意: `[] 中的属性必须存在于被查询类型中,否则就会报错同时查询多个索引类型
```ts
type Props = { a: number ; b: string; c: boolean }
type TypeA = Props['a' | 'b']
//使用字符串字面量的联合类型,获取a和b的对应的类型,结果为: string|number
type TypeA = Props[keyof Props]
//使用keyof操作符取Props中所有键对用的类型,结果为: string | number | boolean

PART16 TypeScript高级类型相关推荐

  1. TypeScript高级类型:联合类型、交叉类型和类型别名

    目录 引言 联合类型 交叉类型 类型别名 注意 结论 引言 TypeScript 是一门强类型语言,其高级类型功能使得开发者能够更加灵活地定义类型并对其进行操作,以便于更好地编写可维护和可扩展的代码. ...

  2. TypeScript 高级类型及用法

    一.高级类型 交叉类型(&) 交叉类型是将多个类型合并为一个类型.这让我们可以把现有的多种类型叠加到一起成为一种类型,它包含了所需的所有类型的特性. 语法:T & U 其返回类型既要符 ...

  3. TypeScript高级类型-Partial、Required、Pick、Omit、Readonly

    Partial (可选属性,但仍然不允许添加接口中没有的属性) ts中就是让一个定义中的所有属性都变成可选参数,参数可以变多也可以少. 我们定义 一个user 接口,如下 interface IUse ...

  4. 【前端进阶】-TypeScript高级类型 | 泛型约束、泛型接口、泛型工具类型

    前言 博主主页

  5. 【前端进阶】-TypeScript高级类型 | 交叉类型、索引签名类型、映射类型

    前言 博主主页

  6. 5.TypeScript入门之TS高级类型(class类)

    上一章节:4.TypeScript入门之TS常用类型(3) Ⅳ.TypeScript高级类型 概述 TS中的高级类型有很多,重点学习以下高级类型: class类 类型兼容性 交叉类型 泛型和 keyo ...

  7. 类型全部为string_TypeScript 高级类型总结(含代码案例)

    // 每日前端夜话 第458篇// 正文共:2600 字// 预计阅读时间:10 分钟 TypeScript 是一种类型化的语言,允许你指定变量.函数参数.返回的值和对象属性的类型. 以下是 Type ...

  8. boolean类型_10、typescript的高级类型

    所谓高级类型,是typescript为了保证语言的灵活性,所使用的一下语言特性.这些特性有助于我们应对复杂多变的开发场景. 交叉类型 将多个类型合并成一个类型,新的类型将具有所有类型的特性,所以交叉类 ...

  9. TypeScript基础入门之高级类型的可辨识联合(Discriminated Unions)

    2019独角兽企业重金招聘Python工程师标准>>> 转发 TypeScript基础入门之高级类型的可辨识联合(Discriminated Unions) 高级类型 可辨识联合(D ...

最新文章

  1. 网络安全工具:Nmap
  2. ug编程内公差和外公差是什么_数控加工编程的主要内容有哪些?
  3. 福利 | 2022全球敏捷运维峰会:跟技术老将畅聊时下数据库、运维、金融科技应“云”而生的技术创新...
  4. Facebook最新研究:配合AR眼镜使用的腕带,可将神经信号转化为动作
  5. PHP - .htaccess设置显示PHP错误 (转)
  6. 贪心算法很简单:跳跃游戏
  7. 全球及中国LCP行业应用项目布局及产能规模预测报告2021版
  8. 怎么隐藏Windows11开始菜单中的推荐面板
  9. 计算机编程常用指令,加工中心几个常用指令的编程技巧
  10. 新iPhone销量将持续走低 因为旧iPhone够用好几年
  11. linux nmon安装
  12. ASP.NET开发框架之HIPPO技术内幕(三)--数据库连接
  13. (转)Astar寻路教程
  14. Unity预览代码中文乱码解决方案
  15. 2021最新!某盘加速下载工具复活了,无需登录,打开即可高速下载(附下载)!
  16. xp系统整个计算机非常慢,xp系统物理内存不足导致电脑运行速度非常缓慢的图文方法...
  17. Python获取打印机读数(东芝泰格)
  18. 对英文单词的词性标注
  19. Linux下线程池(ThreadPool)
  20. 微信小程序 - 日期(起止)选择器组件

热门文章

  1. php年龄,PHP 年龄计算函数(精确到天)
  2. 【调剂】3.13计算机考研其余调剂信息
  3. 超频DIY之『超频FAQ』
  4. 电子商务公司赢利点在哪?
  5. 开幕在即 | 赛宁网安亮相云上软博会线上展会
  6. 线性回归详解及Tensorflow实战
  7. C语言实现1024bit大数加法(1)
  8. 计算机二级office应用软件,计算机二级Office
  9. 最新易支付APP源码+已经优化修复
  10. AD 入门1 一步步画一个门铃电路