typescript学习笔记——基本类型和接口

2019 / 06 / 07

最近公司项目中用typescript,本来也用过一丢丢,觉得这就是个js超集,一个辅助工具而已,没必要学的太深刻,但是事实上还是遇到了各种各样的麻烦,其实对于没有学过java,c++之类的开发来说,系统的学习一下typescript还是非常有必要的,不然会发现里面的报错解决起来非常棘手。ok,开始学习之旅。

正文很可能是从文档

开始之前

写typescript遇到的第一个问题就是会纠结既然js不会限制类型,我们可以在一个数组里放数值,放字符串甚至另一个数组,没有类型的限制让我们开发变得非常灵活,也没有任何阻挡,而typescript却主动去限制了它,很多人会怀疑这种限制的必要性,但是自己被迫限制了很久然后才会明白没有限制其实更多的是坏处。

  1. 首先没有限制可能意味着你并没有明确自己想要得到什么或者输出什么
  2. 其次灵活带来的不安全和无法追究问题所在也会导致开发者花更多的时间去找bug

所以为了写更加让自己放心的代码,我们主动用typescript去限制了他

基本类型

1. 布尔值

2. 数值 typescript支持用二进制,八进制,十进制和十六进制的声明数值

3. 字符串 声明字符串也非常的简单

4. 数组

数组可以通过范型或者一个类型加[]的方式声明

const arr: Array<number> = [1, 2, 3, 4]
const arr: number[] = [1, 2, 3, 4]

5. 元组

很少会用到这个类型,可以看看百科,主要在后端用的多,一个元组经常表示一个数据表的一行数据

6. 枚举

枚举是一个非常好用的类型,enum不光可以用来声明类型还可以用来定义值,比如下边这个可以认为定义了三个常量。

enum type {
SUMMER,
SPRING,
PROMO
}
const summerType = type.SUMMER

编译成js之后,也就是说typescript默认声明enum类型会按照index作为值

var type;
(function (type) {
type[type["SUMMER"] = 0] = "SUMMER";
type[type["SPRING"] = 1] = "SPRING";
type[type["PROMO"] = 2] = "PROMO";
})(type || (type = {}));
var summerType = type.SUMMER;
console.log(summerType);

也可以这么定义

enum type {
SUMMER = 'summer',
SPRING = 'spring',
PROMO = 'promo'
}
const summerType = type.SUMMER
console.log(summerType)

7. Any

这个是入门typescript最喜欢的一个类型,意味着声明的这个值可以被随意的改变类型,但最好不要去使用他

8. Void 没有返回值

9. Null和Undefined

null和undefined本身没什么意义,尤其是undefined

下边的这个代码是可以通过的,因为null和undefined是所有基本类型的子类型。

let a: string = 'a'
a = null

如果配置 strictNullChecks 为true的话,那么上面的代码就会报错,但typescript也鼓励大家去使用这个参数。

如果需要这个值可以为空的话,可以使用联合类型

let a: null | undefined | string = 'a'
a = null

10. Never

这个可以说是typescript最罕见的一个值了,这个以为着你是等不到返回结果的,比如一个专门用来抛出错误的函数

function throwSeriousError(): never {
throw new Error('This is a very serious error')
}

11. Object

object看起来和any差不多,但是事实上在typescript中这个类型很特别,object只能用来表示非原始类型,比如一个序列化query的方法就不能接受非原始类型的参数就需要用到object。

const stringifyQuery = (query: object) => {}
stringifyQuery({ from: 'app', type: 1 })

12. 类型断言

为什么会出现这个玩意呢,其实在其他语言中也会出现类型转化的问题,因为毕竟如果要清晰的告诉编译器你在做什么事情可能非常的难,所以有时候需要强行告诉编译器我需要做什么。

比如定义了一个any的类型的值,但是typescript并不允许你使用他的length方法,因为这个值可能不是string,但是你通过typeof或者其他的方式已经确定他就是一个string了,所以你要告诉typescript我敢断定我现在就是在用一个字符串。

断言可以用尖括号或者as的方式声明

let str: any = 'abc'
let strLength = <string>str.length

或者

let str: any = 'abc'
let strLength = (str as string).length

接口 interface

interface是typescript的非常核心的一部分,很多很多的情况下我们拿到的数据一般并不是一个简单的数据类型,比如一个后端返回的接口或者前端定义的数据结构都可能会是一个复杂的接口。

比如

interface Ball {
color: string
radius: number
x: number
y: number
}

function renderBall(ball: Ball): void {}

自定义的这个类型就叫做接口。

可选属性

interface Ball {
color?: string
radius: number
}

如果有默认值的话,接口的某个值可以省略。

只读属性

interface Ball {
readonly color?: string
readonly radius: number
}

只读属性会被保护,无法修改,这个属性我还没用过。

额外属性

interface Ball {
readonly color?: string
readonly radius: number
[propName: string]: any
}

当接口需要许多不确定的属性时,使用这种方法就可以不用一一定义了。

函数接口

interface Ball {
render: { (text: string): void }
}

额外属性使用中括号表示这个key是一个变量,这个写法类似于es6的新特性可变属性。

函数是通过花括号表示是一个接口,圆括号表示参数的方法。

箭头函数的话可以用下边的这种写法

interface Ball {
render: (text: string) => void
}

类数组对象

interface IndexObject {
[index: number]: string
length: number
}

const indexArr: IndexObject = { 0: 'hello', 1: 'world', length: 2 }

总结

typescript的基本类型比较简单,有一些用的很少,比如元组,有的是提供了能力但不推荐使用,比如null和undefined是其他基本类型的子类和any,可以通过tsconfig.json进行配置,给予这些不推荐的写法警告或者报错。

interface是一个前端开发者很陌生的概念,但是也是typescript非常基本的概念之一。如果可以知道如何写各种各样的接口属性那么就能解决大多数的typescript遇到的问题了。当然这还只是个开始,想要用好typescript需要更多的知识,比如类和类相关的接口。

嗨,请先 登录

加载中...
(๑>ω<๑) 又是元气满满的一天哟