-
Notifications
You must be signed in to change notification settings - Fork 49
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
2016/03/31 针针见血:怎么消除JavaScript中的代码坏味道 #5
Comments
第一个例子是不是有误? |
肿么感觉,看着糟糕代码都是我会写的,心好累 |
我也是这种感觉,槽糕的代码都是我现在在写的 |
|
@flyinhigh 哈哈,前面那个其实是包含 es6 的 template string 的语法(内插值)啦,去了解下就知道了~ |
写得很棒~一点儿小意见...
|
@BuptStEve 很仔细。用新的includes很好,来清除掉怪异的!! |
这个不是去年jsconf的js code smells的ppt吗? http://elijahmanor.com/javascript-smells/ 是不是说明在文章开头原作者和来源好一点? |
@chengmu 说的很对,现在的文章都会在开头说明来源。老文章并没有这些意识 /(ㄒoㄒ)/~~ |
# for free
to join this conversation on GitHub.
Already have an account?
# to comment
本文罗列JavaScript代码中常见的代码坏味道,如临时定时器,双向数据绑定的坑,复杂的分支语句,重复赋值等,对它们进行分析如现场还原,糟糕代码回顾,问题诊断和识别(通过ESlint或其他工具),代码重构方案,给出了怎么写好代码的一手经验~
绕来绕去,很烧脑
问题现场:
如果单词以辅音开头(或辅音集),把它剩余的步伐移到前面,并且添加上『ay』如pig -> igpay
如果单词以元音开头,保持顺序但是在结尾加上『way』如,egg->eggway等
糟糕代码:
问题在哪:
检测出问题:
关于Lint的配置项:如最大语句数,复杂度,最大嵌套数,最大长度,最多传参,最多嵌套回调
测试先行:
重构后代码:
数据对比:
max-statements: 16 → 6
max-depth: 5 → 2
complexity: 7 → 3
max-len: 65 → 73
max-params: 1 → 2
max-nested-callbacks: 0 → 1
相关资源:
jshint - http://jshint.com/
eslint - http://eslint.org/
jscomplexity - http://jscomplexity.org/
escomplex - https://github.com/philbooth/escomplex
jasmine - http://jasmine.github.io/
粘贴复制
问题现场:
我们需要实现如下的效果

糟糕的代码:
问题出在哪:
因为我们在粘贴复制!!
检测出问题:
检查出粘贴复制和结构类似的代码片段 - jsinspect
https://github.com/danielstjules
从你的JS,TypeScript,C#,Ruby,CSS,HTML等源代码中找到粘贴复制的部分 - JSCPD
https://github.com/kucherenko/jscpd
重构后代码:
复杂的分支语句
糟糕的代码:
问题出在哪:
违反了 open/close 原则:
软件元素(类,模块和方法等)应该易于被打开扩展,但是除了本身不要多于的修改。既代码本身可以允许它的行为被扩展,但是不要修改源代码
可以使用诸如检查:
no-switch - disallow the use of the switch statement
no-complex-switch-case - disallow use of complex switch statements
重构后代码:
这时候添加一个代码就不像之前那样该原先的switch,直到它又长又臭,还容易把之前的代码逻辑broken掉。
魔法数字/字符串的坏味道
糟糕代码:
如上面看到的,如Magic Strings,对于诸如Triangle,Square这些就是特殊字符串。
问题出在哪:
这些魔法数字和字符串是直接写死在代码中,不容易修改和阅读。注入password.length > 9,这里面的9是指 MAX_PASSWORD_SIZE ,这样先定义后使用更清晰。同时如果多个地方需要这个判断规则,也可以避免多次修改类似9这样的数字
https://en.wikipedia.org/wiki/Magic_number_(programming)
http://stackoverflow.com/questions/47882/what-is-a-magic-number-and-why-is-it-bad
重构后代码:
1 通过对象
2 通过 const 和 symbols
代码深渊
糟糕代码:
问题出在哪:
奇奇怪怪的 self /that/_this 等
使用一下的eslint:
重构后代码:
利用Function.bind, 2nd parameter of forEach, es6
脆裂的字符拼接
糟糕代码:
问题出在哪:
代码很丑陋,也很啰嗦,不直观。
使用 ES6的模板字符串(字符串插值和多行)
很多工具和框架也都提供了响应的支持,如lodash/underscore,angular,react 等
重构后代码:
jQuery询问
糟糕代码:
问题出在哪:
太多的链式调用
重构后代码:
临时定时器
糟糕代码:
问题出在哪:
out of sync timer 不能确认时序和执行
重构后代码:
等 3s 去执行timer(setTimeout),然后调用 someLongProcess (long process: random time ),接着在循环
使用setInterval fn(其中在进行 long process),还是通过callback传递来反复setTimeout(timer, )
重复赋值
糟糕代码:
问题出在哪:
有些重复和啰嗦
eslint-plugin-smells
重构后代码:
1 嵌套的函数调用
2 forEach
3 reduce
4 flow
不合理的情报
糟糕代码:
问题出在哪:
依赖被紧紧的耦合了
相互调用,耦合!如 product 和 shoppingCart 关系
重构后代码:
1 dependency injection 依赖注入
2 消息经纪人broker
不断的交互调用
糟糕代码:
问题出在哪:
会造成卡顿,多余的计算等
重构后代码:
throttle 和 debounce
匿名算法
糟糕代码:
问题出在哪:
匿名函数是个好东西,但是给函数命名可以帮助我们:
重构后代码:
未明确的执行
糟糕代码:
明确触发时机而不是,写在 domready
问题出在哪:
很难做单元测试
重构后代码:
利用单例模块,加上构建器函数
单例模式(单例有个init 方法,来Kick off) & 构造函数(new Application() -> 在原来的构造函数中Kick off your code!)
双向数据绑定
糟糕代码:
随便看看你们手头的MVVM项目(如Angular的等)
问题出在哪:
很难定位执行顺序和数据流(Hard to track execution & data flow )
(也是Angular1.x被大力吐槽的地方,被React的Flux)
重构后代码:
方案: flux(action, dispatcher, store->view)
React Flux
An Angular2 Todo App: First look at App Development in Angular2
结语
更多的lint规则,在npm上搜索 eslint-plugin 查找
Reference
The text was updated successfully, but these errors were encountered: