当前位置: 首页 > 科技观察

几个一目了然的TypeScript小技巧

时间:2023-03-21 21:59:09 科技观察

TypeScript是一门语法众多的语言。和那些只需要熟悉API的库是不一样的。它更灵活,当然有很多技巧。本篇分享一些很多人都不知道的小技巧,都是学过之后能用的。keyofanyTypeScript有一个内置的类型叫做Record,它的作用是根据传入的索引和值的类型构造一个新的索引类型。它的实现是通过映射类型的语法构造一个索引类型:typeRecord={[K中的P]:T};那么问题来了,如何约束这个K呢?有同学说K不是索引?那应该是string,也就是Kextendsstring。但是JS属性可以是三种类型:string、number、symbol。然后我知道,Kextendsstring|编号|象征。不不不,TypeScript有一个名为keyofStringsOnly的编译选项。如果启用,则仅使用string作为索引,否则为string|源码中Record是怎么定义的:typeRecord={[PinK]:T;};它使用keyofany,这个keyofany可以动态获取key支持的类型吗?让我们试试吧。未启用keyofStringsOnly时:启用keyofStringsOnly时:妙极了,这样可以动态获取当前支持的key类型。当需要将类型参数约束为索引Key时,使用keyofany动态获取比硬编码string|更好编号|象征。object和Recordobject和RecordTypeScript中有三种很难区分的类型,分别是object、Object和{}。其实只要记住object是不能接受原始类型的,其他两个类似,只是{}是一个空对象,没有索引。所以number可以赋值给{},Object类型,但不能赋给object类型:其实看源码就会发现不会用object来约束,而是用Record来约束index类型。这两个其实是一样的。但Record更具语义。Record创建的索引类型,key为任意字符串,value为任意类型:因此,在约束索引类型时,可以使用Record代替object。而且你会在很多源码中看到这种写法,比如下面是Nest.js源码中的:-readonly映射类型可以构造一个新的索引类型,并在构造过程中进行一些修改。例如,构造一个新的索引类型并使所有Keys可选:typeToPartial={[KeyinkeyofT]?:T[Key]}或者构造一个新的索引类型并添加readonly修饰:typeToReadonly={readonly[KeyofT]:T[Key];但是很多人不知道还可以去掉已有的修饰,用-号,减法的意思:比如去掉?是吗-?:typeToRequired={[KeyinkeyofT]-?:T[Key]}然后去掉readonly,自然是-readonly:typeToMutable={-readonly[KeyinkeyofT]:T[Key]}I最近看到Promise.all的类型定义是这样的:类型参数T是一个待处理的promise数组,返回值是Promise值对应的数组,取值类型通过等待。Awaited是TS内置的高级类型,用于提取Promise的返回值类型:返回类型是数组类型,那为什么可以使用映射类型的语法呢?因为数组类型也是索引类型,而索引类型就是聚合多个元素、数组、对象、类的类型,都是索引类型。当然主要是说说-readonly的语法,readonly的修饰可以去掉。这个方法可以这样调用,例如:classDong{name:string;constructor(){this.name="东";}hello(){return'你好,我'+this.name;}}constdong=newDong();东.你好();当以object.methodname的形式调用时,this指向那个对象。但是方法也可以用call或者apply来调用:调用的时候this发生了变化,但是this指向的错误这里没有检查。编译器如何检查出这个指向的错误呢?其实方法可以指定this的类型:classDong{name:string;constructor(){this.name="东";}hello(this:Dong){return'你好,我'+this.name;这样在调用call/apply的时候,就可以检查this指向的对象是否正确:而且TypeScript还提供了一个内置的高级类型ThisParameterType,用于提取this的类型:它的实现是很简单,就是通过模式匹配把this的类型提取出来,返回给infer声明的局部变量:?语法,也可以通过??指定默认值:constdong=data?.name??'东';编译后会变成这样:做了空值检查,同时也设置了默认值dong。一个非常简单好用的语法,但是很多人写了ts还是不会用。总结TypeScript有很多灵活的语法和很多技巧。今天分享一些你可能不知道的技巧:keyofany可以动态获取key支持的类型,根据keyofStringsOnly的编译选项,可以用来约束索引。object不能接收原始类型,但是{}和Object都可以,这是它们的区别。Object一般被Record代替,约束索引类型更语义化。映射类型语法可以创建索引类型,并添加只读或?修改,其实也可以用-readonly,-?去掉。?和??分别代表空判断和默认值,这是写TS很常用的语法。可以约束this的类型,也可以通过内置的高级类型ThisParameterTypes获取。这几个tips是那种看一遍就可以,下次写TS类型的时候可以用到的。