菜单 学习猿地 - LMONKEY

VIP

开通学习猿地VIP

尊享10项VIP特权 持续新增

知识通关挑战

打卡带练!告别无效练习

接私单赚外块

VIP优先接,累计金额超百万

学习猿地私房课免费学

大厂实战课仅对VIP开放

你的一对一导师

每月可免费咨询大牛30次

领取更多软件工程师实用特权

入驻
0
0

前端程序员做了这件事就是工程师了

原创
05/13 14:22
阅读数 210

课程推荐:web全栈开发就业班--拿到offer再缴学费--融职教育

function outcome (value) {}
复制代码
这是个标准的 JavaScript function。每个前端开发者(你以为)都是这样写自己的 function 的。和那一夜的你一样,不慎为自己的疯狂付出了代价。但这个代价还只是个形参,他存在,但他的真实却是你未知的。他有可能是一周之后身体上出现的点,也可能是一年之后墓碑上出现的字。不确定是确定的,未知是痛苦的,刺激是必然的。你夜不能寐,你的精神持续承担着各种结果权值乘以概率的数学期望。
为此你决定建立单元测试,但是虚荣让你先走访了一个可以信任的同僚,一个禅意足得让你恶心的恶棍。他在打坐中半睁开了眼,他告诉你说
function outcome (value?: DefinetlyNotADisease) : VeryVeryMinorResult {}
复制代码
你喜欢思考,但大多数都是些“斑马到底是马还是驴”的问题。禅师的一席话叩开了你内心世界的一个大门。回家路上你思考。 到底你的痛苦是来自于对结果的未知、还是未知的结果。回想起禅师的话:“确定性是工程学的基本语元”好像能懂,和“未知的未知会因为无知而被误作已知”。你心想这都特码啥玩意。但你还是照做了。
忘掉恐惧之后的你开始隐约忿恨并且很困。

一个梦:并不知道什么是什么

npm install -g typescript

tsc --target "ES5"

在睡了完美的一觉之后,你感觉重生已经了,你开始回想起来不久前的经历。你开始怀疑一些莫名其妙的问题,比如你是不是你。是被 TypeScript 杀死掉的替身,还是你得到了升华。你不想成为另一个你、一个死的你或学习做为另一个他。想到这,斑马到底是马还是驴的困惑感又涌上了喉咙甚至到了鼻窦。就这样,你又回到了在高高的壁格上供奉着的同僚面前。这次他说,JavaScript 是TypeScript 的子集,可以算 TS 的一种。然后放出一招

#!/usr/bin/env node// 啥也没干,只把扩展名改了。TypeScript 升级完毕
let fs = require('fs');const lookfor = 'src';function recurr (lookfor) {fs.readdir(lookfor, (err, files) => {files.forEach(a => {let path = lookfor + '/' + a,f = fs.statSync(path);if (f.isDirectory()) {recurr(path);} else if (a.match(/.js$/)) {fs.renameSync(path, path.replace(/.js$/, '.ts'));}});});}recurr(lookfor);console.log('done! simple like that!')
复制代码
“不用改一行代码,不用改一行代码,不用改一行代码(除了 function outcome)”,禅师说话间调高了音量、混响、合成器,把最不富哲理一句话 echo 了重要的3遍。你一下子明白了谁还是你。谁只是多了一些新的可能,无论谁如何抗拒你,谁都可以接纳自己。你满意了,开始像马又像驴地飞奔回家。然而你还是有很多困惑,无法自拔,同事们感觉最近有点也爱胡说八道了,觉得你也有供入壁格的可能。他们渐渐疏远了你。
你知道你没有变,你开始在原来的代码里加上类型声明,类型声明简单至极,同时又丝毫不碰原来代码逻辑:
function outcome(val: Even) : void { // 入参为 Even 的实例;返回值是 void
let temp: string; // 字符
let ties: number; // 数字
let tombs: Array = [1]; //类型为 number 的数组
let mount: Observeable; // 会onNext string 类型的 Observeable
let what : any; // 任意类型,类型之前的 JavaScript 变量都是 any;
}
复制代码
你开始总是能提前知道。提前知道很多事情。你开始怀疑写出代码一次就能运行不是疯话。你不再需要在几个文件之间来回来去查,你不再担心拼写,不再担心复制的东西漏改一些,你开始提前知道你不能提前知道一些事情。
在接下来的几天里你配置了 tsconfig.json 和你的编辑器插件,智能提醒实时的飞到你的面前。你开始有兴致的去调整 tsconfig。
你发现它已经内置了 babel 的编译能力,可以编译出 ES5、ES6、ES7 和一个不知所云的 ESNext。
对 module 的规范也华丽的支持 Node 的 commonjs 、 ES7 的 import,甚至支持 AMD、system、UMD、ES2016、ESNext。
{ "compilerOptions": { "outDir": "./dist/", "noImplicitAny": true, "sourceMap": true, "module": "commonjs",/ AMD system UMD ES2015 ES2016 ES2017 ESNext / "target": "es2015", / ES3 ES5 ES6 ES2015 ES2016 ES2017 ESNext / "jsx": "react", "allowJs": true }}
复制代码
代码渐渐亮了起来。微软提供大量的编辑器 ts 插件,实时编译真实提醒,不像 Sublime Text 默认的单词提醒(和禅师本人)疯话连篇。

微软提供大量主流编辑器的 TypeScript 插件。真内容提醒

TypeScript 语义可以区分出错误的引用、错误的传参、错误的赋值。合作不再是开会开会开会
渐渐地,你开始了对一直躲藏在 any 背后的 Object 们大开杀戒
let enumDom : {[key: string] : number} = {}; // key 是 string,value 是 number 的 object;class DLabel extends DeafElement{ // virtual class,直接当做 type 使用 width: number; height: number; text: string; fontsize: number;}enum DNodes{ // 枚举中特殊的一种。普通的一种太普通不列了 net = 'net', col = "col", from = 'from', to = 'to', place = 'place', trans = 'trans', sition = 'sition'interface Point{ // 工程合作中最高效的工具,软件工程几十年的行业标准,interface x: number y: number}
复制代码
在这个过程里,你的代码越来越规范,继续杜绝 any 还需要对父类子类什么都 cast 一下。
比如 document.getElementById 返回通用的 HTMLElement。它被 cast 成 HTMLCanvasElement 从而 post 知道了有 getContext 方法。而那些沙瓤西瓜们完全不会知道。
file
变量前给个可以 Cast 多态,在 tsx 里换成在后面加 as

你发现同事们开始用起来 ES7 的一些玩具。当然这些你早就用上了并且 tsconfig 决定如何编译。
"use strict";// target 到 ES2017 时下面这些都不出现,await 就 await// 当 ES7 的特性被 tsconfig 的 target 指定到 ES6 时,tsc 会用 ES6 的 Iteration & Generation 特性来编译实现// 鬼知道 target 到 ES5 会怎么编。总之能实现,就是var awaiter = (this && this.awaiter) || function (thisArg, _arguments, P, generator) { return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator"throw"); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); });};
复制代码
做完了这些,你的开发速度靠着准确度的提升和提醒辅助输入已经飞快的像一套冲入云霄的超音速家燕。
你发现你的项目中总有外部的 js 交流,这些 js 如果有 type 定义……禅师的脑电波传来,你需要一些 npm 包。
package.json:
..."devDependencies": {"@types/koa": "^2.0.39","@types/lodash": "^4.14.77","@types/node": "^8.0.33"},...
复制代码

他们内部是一些 *.d.ts 文件

file
@types/react React 的 types

而有一些由 ts 开发、编译到 js 的 NPM 包已经集成了 d.ts 的类型声明了
file
Rx 的内容

TS 代码开始可以和 JS 的互相引用,被 JS 引用时就像 JS,被 TS 引用时就像 TS。

#include

你的思绪跳到了某个青葱年代,一切恍若隔世,但是有仿佛没有走远。你感到佛龛对你张开,里面却意外的缺少了某种膈应人的气息。你开始自发的使用 ts 写所有的项目,也开始逐渐习惯给缺少类型定义的开源库提交 @types 包。随着这些快速的变化你为公司写的底层库越来越多也被引用的越来越多。
远方的乌云背后穿透出点点阳光,你看到风起云涌的天边降下一片片豪雨。它们排列出深浅不一的一道道垂直的暗条,外面明亮的天空却闪耀的让人眼花。迎面吹的风仿佛寄来泥水和混沌气味的些许痕迹。
突然清醒过来以后,你发现一切竟然已经过去 3 年了。禅师已经东窗事发,因长期摸鱼不写码被强行解聘。TS 却经历了普及和成熟。刚入职的小同事也在侃侃而谈某个新特性。一切都和 3 年前截然不同了。你也已经认知到 closure compiler 等等其他的类型检测工具。你揉了一下眼睛,你感到认不出自己也认不出自己的代码。你发现自己可能就是那个曾经的禅师。你就坐在他曾经最喜欢的飘窗地垫上望着天空发呆。甚至现在你曾经连此刻是此刻还是 3 年前都已经混淆了。你开始想到未知的未知会因为无知而被误作已知而自己是个白痴。突然这时,你却清楚地听到拿着外卖的两个小同事,他们一边聊天一边走过,口中讨论“斑马到底是白马黑条,还是黑马白条?”听到这里,你非常斩钉截铁的插入话题立即回答了他们:
都不是,是驴。

作者:Astatine
链接:https://juejin.im/post/6887874578748538887
来源:掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

发表评论

0/200
0 点赞
0 评论
收藏
为你推荐 换一批