typescript

10,054 阅读5分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第9天,点击查看活动详情

什么是ts?

ts是js的超集,是添加了类型系统的js,适用于任何规模。

ts的优点(特点)?

  1. ts的静态类型
  • 系统按照类型检查的时机来分类,可以分为动态类型和静态类型。动态类型:在程序运行时才会进行检查。静态类型:是在编译阶段就能确定每个变量的类型,ts在程序运行前将其编译成js,在编译阶段就会进行类型检查
  1. ts是弱类型
  • 类型系统按照是否允许隐式类型转换来分类,分为强类型和弱类型。ts是完全兼容js的,不会修改js运行时的特性,是弱类型。
    比如:

image.png
3. 适合任何规模

  • ts非常适合大型项目,带来更高的可维护性,以及更少的bug。
  • ts在中小型的项目中因为有类型推导也不需要完全手动声明了,反而还增强了编辑器的功能,提供了代码补全、接口提示、跳转到定义、代码重构等能力。提高开发效率,如果觉得严格,还可以修改编译选项,降低标准。
  • ts还可以与js共存。可以同时使用js和ts。可以在不修改js文件的前提下,编写一个类型声明文件,实现旧项目的渐进式迁移。
  • 一些第三库原生支持了ts。在使用时就能获得代码补全了,比如vue3.0
  • 有一些第三方库原生不支持ts,但是可以通过安装社区维护的类型声明库(比如通过运行npm i --save-dev @types/react来安装react的类型声明库)来获得代码补全能力。
  1. 与标准ECMAScript同步发展

安装ts

image.png

基础

原始数据类型

  1. 布尔值:Boolean
  2. 数值:number
  3. 字符串:string
  4. undefined
  5. null
  6. void(没有返回值的函数,ts才有)
使用Boolean来定义布尔值类型

值:类型

image.png

使用number定义数值类型

image.png

使用string定义字符串类型

image.png

空值void

js中没有空值的概念,但在ts中可以用void表示没有任何返回值的函数

image.png
*注意:声明一个void类型的变量没有什么用,因为你只能将它赋值为undefined 和null

image.png

null和undefined

使用null和undefined来定义两个原始数据类型

image.png
两者与void的区别:undefined和null是所有类型的子类型,也就是说undefined类型的变量,可以赋值给number类型的变量。

image.png

image.png
而void类型的变量不能赋值给number类型的变量。

任意值 any

任意值用来表示允许赋值为任意类型,如果一个普通类型,在赋值过程中改变类型是不被允许的,但如果是any类型,则允许被赋值为任意类型。

  • 任意值的属性和方法:在任意值上访问任何属性都是允许的(哪怕没有该属性,编译时不会报错,但是运行时会报错的)。

image.png
也允许调用任何方法:

image.png
声明一个变量为任意值之后,对它的任何操作,返回的内容的类型也都是任意值。

  • 未声明类型的变量:会被识别为任意值类型。

image.png

类型推论

如果没有明确的指定类型,那么ts会依照类型推论的规则推断出一个类型。
如下所示,最开始编译时被没有指定类型,但在编译的时候会报错,是因为ts在没有明确的指定类型的时候推测出一个类型,这就是类型推论
(定义的时候直接赋值但没有声明类型的话,会按声明时值的类型来进行类型推导)

image.png
如果定义的时候没有赋值,不管之后有没有赋值,都会被推断成any类型而完全不被类型检查:

image.png

联合类型

表示取值可以为多种类型中的其中一种(必须是其中的一种)。使用 |分隔每种类型。如:

image.png

  • 访问联合类型的属性和方法
    当ts不确定一个联合类型的变量到底是哪个类型的时候,我们只能访问联合类型的所有类型里的共有的属性或方法

image.png
上述示例错在length属性不属于number,必须是string和number共有的属性才可以。

image.png

对象的类型------接口

ts中使用接口(interface)来定义对象的类型。如:

image.png
注意:上述示例中,我们定义了一个接口Person,接着定义了一个变量tom,它的类型是Person,这样,就约束了tom的形状必须和接口Person一致。

  • 如果想少写某一个属性,用可选属性即可。用?表示(但仍不允许添加属性)。如下:

image.png

  • 如果想添加某一个属性的话,用任意属性,用[propName:类型]:值类型。如下:

image.png
注意:一旦定义了任意属性,那么确定属性和可选属性的类型都必须是它类型的子集。

image.png
上述示例报错了,因为任意属性的值允许是string,但是可选属性是number,number不是string的子属性,所以报错了。而且,报错信息,此时{name:'tom,age:25,gender:'male'}的类型被推断成了{[x:string]:string | number;name:string;age:number;gender:string},这是联合类型和接口的结合。
一个接口中只能定义一个任意属性,如果接口中有多个类型的属性,则可以在任意属性中使用联合类型:

image.png

  • 只读属性 readyonly,对象的设置字段只能在创建的时候被赋值,后期只能读不能修改

image.png
创建的时候赋值了,但后期有再次赋值修改,所以报错,因为是可读属性。

image.png
注意:只读的约束存在于第一次给对象赋值的时候,而不是第一次给只读属性赋值的时候

image.png
上述示例,报错有两处,第一处是在对tom进行赋值的时候,没有给id赋值。而是给tom.id赋值的时候,由于它是只读属性,所以报错。