TypeScript 文字教程(波大神分享)

TypeScript

首先第一个点,TypeScript 学起来并不难,大家要先从心态上不要太过于抗拒。

前端的所有知识基本上都是这样,学会了,就跟 1+1 等于 2 差不多,通透了非常简单,所以心态上要放好,如果心态上抗拒,基本上来说掌握起来就会变得困难。

第二个点,我尽量从学习方法的角度,去跟大家分享如何去学,而不是直接告诉你这个知识是什么样!所以大家在听课的时候,建议也是从这个角度去思考,最重要的是,要知道如何去学。

什么是 TypeScript

和其他语言不一样,JS 非常灵活,没有约束,所以基本上来说,别人的 JS 代码阅读起来是非常困难的。

就比如读源码,在前端行业是一个高逼格的事情,但是你学 Java,你会发现读源码就是一件非常自然,而且是大家都会去做的一个事情,因为 Java 的源码读起来非常方便。学 Java 的时候,大家都觉得读源码没什么了不起,就是因为强类型语言带来的好处。

TypeScript 就是给 JS 添加的一层语法规则,我们学 TypeScript,其实就是学一套语法规则。

小程序的 Taro 框架,大家估计都有耳闻,是我见过的,ts 用得最好的框架。大家可以看看,假设我现在对 Taro一无所知,是如何能够直接上手开发。

2019-12-06 16.45.17.gif

大家可以看一下,假设 View 组件,我们事前一无所知,通过 ts,就可以很快速的知道它由那些 props 能够使用,只要对 react 熟悉,基本上来说,这种新的 UI 组件用起来是没有任何障碍的。

所以,在 ts 的声明文件用得非常好的情况,大家学会了 ts,基本上 Taro 也能轻松无压力的使用。

ts 还帮助我们快速的了解一个变量的类型,一个函数的入参与出参。

这一点非常重要,只要在写代码的时候类型声明做得好,那么再维护代码的时候就非常轻松。重点就在于维护简单!!

经常改bug的同学应该会体会比较深刻。如果出了一个bug,正常的只用js开发,很难肉眼就把bug抓出来,我们以前要借助各种调试

现在我改bug的一个感受,很多bug基本上通过bug现象,和数据类型,大概就能猜到哪里出问题,也能够很方便的读懂其他同事的代码。

这就是可维护性。我们说代码质量,在团队协作中,可读性和可维护性一定是占最高优先级的。

然后就是其他的一些边边角角的优点,大家都比较熟悉了,都在说,比如写代码的时候直接能够发现错误啊,代码提示啊等等。但是typescript的使用会带来额外的代码量,这个有的人会接受不了。这个额外的工作量并不小。

image-20191206165309554.png

就比如说,antd pro的官方demo,基本上每个页面都会用很长的一段类型声明来描述每个数据类型。任何一个用到的数据,都必须有对应的声明描述。你不用的话,就不是在用typescript了。

根据我的经验,这不会影响工作进度,不会因为typescript导致你加班多久多久。反而是因为一个小bug,有可能你会加班一晚上甚至一整天。

基本上来说这种数据声明,其他的语言都逃不掉。例如Android开发,swift开发,包括Flutter的Dart开发。都逃不掉对进行类型声明,所以虽然多出来一些工作量,但不会影响进度,并且其他开发都会做,所以大家不要因此心生抵触。

TypeScript 在项目中的基本使用

第一种常见的方式,就是针对以前已经用 js 代码写好的方法啊、模块呀、框架啊等进行描述。因为以前的代码很多不是用 JS 写的,但是又要享受 ts 带来的便利,所以 ts 经过很多个版本的迭代,找到了一种比较好的方式来描述已经存在的代码。

image-20191206165809051.png

这种单纯的描述文件,都以 .d.ts 结尾。另外一种,就是可以存在于任何 .ts.tsx 文件中。

以一个 React 的组件来举例,我们一个页面组件包含的元素大概如下:

  1. index.tsx

  2. api.ts 数据请求

  3. interface.d.ts 该页面可能会用到的数据的类型描述

  4. commonets 子组件

  5. model.ts 数据管理中心

  6. index.scss 样式表

  7. images 图片资源

比如我们公司的一个项目,用 react native 写的,一个页面组件包含的东西:

image-20191206165909710.png

当然也不是绝对的,如果一个组件需要的描述类型比较少,就不用单独写在一个文件里。我的做法是直接在 api 文件里声明:

image-20191206170005972.png

例如这个组件,只有一个接口,只有一份数据需要单独描述,根据实际情况灵活来做就行。

那么剩下的东西,就是如何使用 TypeScript 支持的语法,来描述我们在实践过程中遇到的数据了。

怎么描述,主要的就是看官方文档,我带着大家一起过一下,大家下来要花一个小时详细阅读。描述基础数据类型,很简单。

image-20191206170121265.png

官方文档的语法,是在ES6的基础上来扩展的,官方文档也认为 ES6 是自己的语法之一,所以官方文档有许多 ES6 的知识点。

如果对 ES6 比较熟悉,这些知识点基本上可以忽略。

image-20191206170252222.png

这几个点一个一个过一遍。

1. 基础类型

基础类型非常简单,基本上来说大家自己都能学得会,需要注意的一个点就是类型断言。

image-20191206170342911.png

实践中一般我们都只用 as 语法,意思就是 强制类型约束

image-20191206170358529.png

例如本来 10 是一个数字,但是我强制要求它变成一个 string,然后ts规则就会认为 a 是一个字符串。

这个就是在实践里,我们常常会在ts能力达不到的地方使用。具体要用的时候去感受,言语很难说清楚。

2. 变量声明

官方文档第二个:变量声明。说的是 ES6 的 var/let/const 这些东西,忽略,大家自己去看。

3. 接口

官方文档第三个:接口。对应的是大部分后端语言里的概念 interface。

在 JS 里,就是用来描述 JSON 数据的。

例如,在 antd pro 官方文档中,有一个 JSON 数据长这样:

image-20191206170605747.png

它的描述接口

image-20191206170617675.png

就长这样。就很简单,基本上一一对应。

然后就是一些语法上的知识,例如可选啊,只读啊,继承啊等等。

这个大家自己阅读文档学习。

但是我们在使用 JSON 数据的时候都知道,有很多非常刁钻的场景。例如我们也不知道这个 JSON 对象会有哪些字段,可能是这几个,也可能会多加几个。

image-20191206170755523.png

这种情况就使用可索引的类型来描述。

4. 类

官方文档第四点:ES6 的类 —— class,略过。

5. 函数

官方文档的第五点:函数。

有很多 ES6 的知识,然后另外一个要描述清楚,这个函数传入的参数是什么,以及返回的数据类型是什么

image-20191206170828986.png

然后其他的就是 ES6 的东西,不再多说,略过。

6. 泛型

官方文档第六点,泛型。整个 TypeScript,这是第一个难点。基本上来说,懂了泛型,其他的就不会是问题。

因为有类型约束,所以 TypeScript 失去了很多灵活性。但是有的时候,我们又希望数据类型具备一定的灵活性。但是这种灵活性,又想他带有一定的约束。所以就产生了泛型这个语法。

以数据请求为例,在 antd pro 的官方案例中,请求的函数 request:

image-20191206170929659.png

我们知道这种异步请求函数返回的结果,一定是一个 Promise 对象,每一个接口请求都是返回的 Promise。但问题就在于,每个接口,返回的数据肯定是不一样的,但是我们在具体使用之前,谁也不知道具体的场景里返回的数据是什么。所以这里就用泛型来表示一个变量,既然我不知道是什么,那我就用一个变量来占位。所以返回结果的描述,就变成了 Promise<T>

我们在使用函数时,传入这个变量,ts 就能够推导出来返回结果是什么:return request<AnalysisData>('/api/fake_chart_data');

request 在使用时传入了变量 AnalysisData ,这个变量时一个数据的类型声明,声明的就是返回结果

[图片上传中...(image-20191206171045694.png-df7a12-1575641450209-0)]

image-20191206171107161.png

我们在约定请求返回结果时,也会用到泛型,例如,我们知道返回结果里,一定会有是否成功的一个字段,success,也一定知道还有一个字段,data。但是我们不知道 data 的具体类型,因此用泛型来声明返回结果。

image-20191206171142366.png
image-20191206171150256.png

到具体的场景里,data 是什么,我们就传入什么。

这个就是泛型,理解了很很简单。

关于泛型的解释,官方文档反而弄复杂了,所以如果我说的听懂了,就可以不用看官方文档。

7. 枚举

枚举:就是一个简单的枚举语法,由于在前端里,1个是我们需要的字段有三个,枚举表示不了,key,value,以及对外显示的字符串,所以前端逻辑里用枚举比较少,略过。

8. 类型推导

官方文档第八个知识点:类型推导

类型推导就是根据已经存在的条件,自动推导出来数据的数据类型是什么。因为有自动推导,我们可以在很多地方不用写数据类型声明。

image-20191206171254695.png

例如这个例子,useState 的初始化数据类型已经很明确,非常容易就推导出来,那么 store 的类型就不需要再额外声明一个。

image-20191206171306334.png

即使没有声明,提示也准确的告知了 store 的类型格式。这个是 TypeScript 自身的特性,使用的时候,我们发现能自动推论出来时,不去声明就 OK,这一点略过。

9. 类型兼容性

官方文档第九点:类型兼容性。就是什么样的类型能够赋值给什么样的类型。

例如 a = 10, b = 'hello',类型不同,a 不能赋值给 b,完全不兼容。但是当 a, b 相同时,就能相互赋值。

我们在使用时,经常看到这类报错提示:

image-20191206171402767.png

实践中这类提示非常多,大家肯定会遇到,这就表示,你想要赋值的两个数据类型不兼容。当完全相同和完全不同时,大家非常容易理解。但是当包含关系时,就需要注意:

image-20191206171430070.png

两个类型声明类似,但是 Person 两个值,都是可选的

我想要将 p1: Person 赋值给 p2: Person2 时,不兼容,因为 p2 的值必须有,但是 p1 可以没有。所以 p1 不能赋值给 p2,会出现异常情况。

image-20191206171502911.png

他最终的错误提示,就是说 undefined 不能赋值给 string,其实就是 name 的属性不兼容。但是反过来,就可以:

image-20191206171522892.png

就不会因为类型不兼容报错。

这个知道报错的原因,就行了,大家不用过于在意这个点,官方文档略读即可,因为你使用时出错了会告诉你。

10. 高级类型

官方文档第 10 个知识点:高级类型

这个高级类型,大家要作为 TypeScript 的进阶学习来看待,初学时可以不用太在意。例如你 TypeScript 用过一段时间,比较熟悉了,再来学习他,我们在实践里,大多数情况下用到比较少,不过会用于解决一些非常复杂的数据类型。

我的建议是暂时略过,再理解了这些高级用法存在的必要之后,再专门花一个下午的时间来专项攻克。具体的知识点,官方文档说的很清楚,所以本次分享略过。

但是大概读一下也可以,有一些非常简单的,也有一些非常复杂的,还有许多框架层面的东西,经常用到这些高级语法。

11. Symbols

ES6 的知识点,略过。

12. 迭代器生成器

ES6 的知识点,略过。

13. 模块

ES6 的知识点,略过。

14. 命名空间

在一个专门的声明文件里,.d.ts

image-20191206171713497.png

我们可以这样,直接导出声明,不过使用时,需要引入才能用

image-20191206171724662.png

我们也可以专门用一个命名空间包裹起来

image-20191206171734971.png

那么在项目中其他文件中使用时,直接用即可,不需要引入 test2

image-20191206171746128.png

这个就是命名空间,很简单,关键的地方在于命名空间的名字必须是唯一的。

15. 模块声明

然后就是模块声明,declare module ‘react’

它的作用就是我们刚才说的,使用声明文件去描述一个已经存在的js库时,常常用到的语法

image-20191206171803996.png

要注意它与命名空间的差别

image-20191206171938048.png

直接这样使用即可。

16. 模块解析

ES6 的知识点,略过。

17. 声明合并

我实践里面用得很少,有点忘了,感兴趣的可以去阅读以下,略过。

18. React的结合使用

待会儿说。

19. 装饰器

ES7 知识点,略过。

20.

我几乎没用过,参考阅读,略过

21.

我几乎没用过,参考阅读,略过

你看,其实官方文档没有那么复杂,只要梳理清楚,基本上两个小时,typescript就掌握了。关键的就是心态。不要因为新增一个东西,就觉得压力很大,其实掌握了学习方法,这些新出的东西都是纸老虎。

如果你自己给自己太大的压力,反而是障碍。

---------------提问环节的回答--------------

tsx是 react文件,

ts就是js文件

.d.ts是专门的类型声明文件,不能写JS逻辑

interface就是接口,但是在TS里没有具体的逻辑上的含义,就是用来描述数据类型,但是也可以继承等

泛型不能是any的,因为泛型有一个简单的约束,就是传入的值和需要的值类型要保持一致。

any就是完全没有约束。

有泛型就表示有约束啊,any没约束,默认值那个就是为了干掉报错。

typescript的依赖反正都是自动引入的,用的时候自己可以关注一下变化,namespace在有依赖的时候,会自动import进来。

泛型没有什么特别,就没了呀,就只要一个用法。至于嵌套泛型啊,什么的,这些都是你实际用的时候,自然而言就能够感受到的,我觉得没必要去可以强化它的复杂度。

https://www.tslang.cn/docs/handbook/mixins.html 大家下来还是要过一次官方文档,按照我说的,最多2个小时就够了

有一个心态要明确的就是,并不是说官方的,就一定是最佳实践

就包括react团队,虽然他们把这个框架开发出来了,但是他们不一定是用得最好的

所以针对这些新出的东西,理解了基本使用之后,要有自己的思考

包括react他们自己也在不断的纠正自己的缺点,所以这个东西都是不断进步的

React

首先react 其实没什么特别的,就是正常的使用,以函数式组件为例,其实就是函数的用法。

image-20191206174632180.png

例如这个函数组件,其实就是声明传入的参数数据类型。

然后class语法也是一样。

image-20191206174649797.png

用了两个泛型变量,分别表示当前组件的props类型和state类型。

image-20191206174702897.png
image-20191206174708873.png

他内部的声明就很简单,所以class语法声明组件也不复杂。

两个泛型,唯一特殊的地方就是JSX,也就是组件。在使用时,属性和props是对应起来的。

image-20191206174746850.png

这些传入的属性,就是props声明的类型。

然后就没有了,react 就这样简单。

因为有typescript来声明约束props,所以之前react提供的校验方式就可以不用了。

image-20191206174816266.png

这个东西,可以不用了。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,928评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,192评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,468评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,186评论 1 286
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,295评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,374评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,403评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,186评论 0 269
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,610评论 1 306
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,906评论 2 328
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,075评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,755评论 4 337
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,393评论 3 320
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,079评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,313评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,934评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,963评论 2 351