[Day30] 浅谈重构(refactoring)与两把刷子

铁人赛的最後一天,让我们先来简单的聊聊重构,这部分是笔者之前在看「大规模重构」这本书时整理的内容,目前只看了前几章,所以能分享的还很有限,但到目前为止我很喜欢作者的观点和态度。

重构的 what 和 why?

重构(refactoring)指的是「在不改变外部行为的情况下,重组程序码的过程」,也就是对於一般的使用者来说,重构前後的差异是不会被感觉出来的,而重构的目的是把原本隐晦、不易理解的程序逻辑、语法、撰写风格等转换成对其他开发者更容易上手和友善的程序码。

先测试、再重构

有些时候或多或少都会有一种想要重构自己或他人程序码的冲动,但要特别留意的是,在还没有足够的测试覆盖率前,千万不要贸然重构,因为有不小的机会,会改坏了某个功能而不自知,很多看起来莫名其妙的程序码,常常有它的涵义在,可能是针对当下的某个 bug 采取的某种 work around,也可能是後来的开发者因为需求变更而随手加上的逻辑,总之, 当你有一种「蛤,这在写什麽」的感觉,有一种想要直接把它删掉的冲动时,就更要小心! 不是不要重构它,而是要更小心谨慎的处理它。

可能的话千万记得,先测试、再重构。

另外,重构时还有一种情境很常遇到,就是原本只想改重构某个范围的程序码,但改者改者却发现这个功能到处都被使用、有彼此相依的情况,进而导致重构的范围越来越大,又或是进入了某种重构的心流後,一发不可收拾,甚至开始包山包海。这几种情况都要特别留意,因为很容易让 Code Review 的人很难看懂,如果可以,请试着把重构范围缩限在他人能够审视的范围(这句话其实是特别在跟我自己说的,对不起了同事,伤了你们的眼睛 ?‍♂️)。

了解当时程序的撰写脉络

当你试着要开始重构某段程序码时,可能的话也可以和当初处理这段程序的人稍微讨论看看(git blame 是个好东西),了解当初会这样写是否有什麽原因,如此,你就有机会避开前人处理过的地雷,否则别人当时这麽做可能是为了让你不要踩到这个洞,但你却挖了个洞给自己跳。

书中这句话是这麽写的:「每行『坏』程序码也同样是要试图解决某个问题。如果盲目地重构它,你可能招惹原作者小心翼翼避开的臭虫或陷阱。」

和当初的开发者讨论,除了能帮到自己外,也可能帮到对方,也许对方开发时真的没注意到这样的写法有什麽不妥,与对方讨论更可以让对方有再次思考和学习的机会,我想只要态度是开放的,大家都很愿意互相学习改进,现在你发现了这个问题与他讨论,未来或许自己写的程序有问题时,对方也会愿意和你讨论,双方都能有互相进步和成长的机会。

为你自己开始重构

最後,和测试一样,当产品时程很赶的时候,通常很难会有额外重构的时间,但还是要多体贴三个月後的自己,如果现在写的自己就已经看不懂的话,怎麽能期待他人或三个月後的自己看懂呢?有些时候你不需要一段完整的时间来进行重构,可以针对这次发的 Pull Request,自己再看过一次,想想有没有什麽更好的写法就很足够了。

後记:React 前端工程师的两把刷子

开始这次铁人赛後,周围就常听到有人捡到新的刷子,不然就是希望我用刷子帮忙刷东西...XD。这次之所以会决定参赛,起初完全是同事 Ken 说服我,说一天只要 300 字,随便一篇 3000 字的文章就可以拆成好几天了,想想好像蛮有道理的,过去曾参加过铁人赛、深知最大的敌人不是系统字数而是自己的我,还是好傻好天真的相信了。话虽这样说,但 Ken 也是真的每天和我一起赶稿的好队友。

BTW,他昨天午夜在写最後一天文章时,突然对我飙骂脏话,我想说怎麽了,难道是睡过头忘了发吗?原来是因为他直接在铁人赛网站用内建的编辑器写文章时,快写完的时候不小把视窗关了!所以原本写的东西都...都...从记忆体挥发了...,恳请大家可以去他最後一天的文章给他一点鼓励...毕竟他真的写了两次(传送门:Day 30 - Finite State Machine x XState 推荐学习资源)。

一开始我订的题目其实是「今晚我想来点笔记时间」,目的就是督促自己每天看一点新东西,然後做个纪录就好,符合一天 300 字的原则,後来某天晚上洗澡时,突然想的,想说不然来整理一下 TypeScript 和测试的内容好了,於是刷子的题目就这样出来了。

除了同事 Ken 的鼓吹之外,推倒骆驼,让我马上决定答应要参加的则是前同事 ycchiuuuuJen 的询问,他们都是我在前公司就很喜欢的夥伴,所以我很快就答应了。真的好在有参与组队,特别是在我写完 TypeScript 的内容後,觉得已经满足个人目标、有点没有方向下一个要写什麽的时候,因为有了不能让团队因我而弃赛的压力,於是就每天一篇又一篇的产出来了。还记得有一天,原本每天都最准时发文的队友突然还没发文且失联,心里不禁一想,难道我们要断赛在今天了?然後,我...我终於就可以不要是因为我而松一口气了吗?

看到今天就知道我队友最後还是有在当天发文,而且还依然是我们三个里面最早发的 XD。

最後,感谢有 follow 本文章的读者,同事 AndyKyle 虽然老是在底下留干话,跟我说他原本都只会用 any...,但还是很谢谢你们的留言,特别是在後期几乎没有读者回覆时,让我的文章还能保有一点点热度和回应,也谢谢 TD 告诉我他觉得我的内容对读者是有帮助的,而且他还说看完後他决定明年要在认真参加一波(咦?),大家明年敬请期待 TD 带来更精彩的内容!?

总之,今年很开心能再次完赛,终於可以放心的喊出「铁人赛臻融一」~!。


<<:  Google Sprint 读後分享与参赛心得

>>:  Day30 file system, inode

Day9-元件沟通传递(part1)

元件之所以很强大是他还有个资料传递功能,让各个元件互相沟通,今天就要来研究他到底要怎麽传资料! pr...

pug 基础介绍(2) DAY100

Jade 汇入外部 JSON 资料内容 这里我们先自行新增2份 jaon档 **menu.json*...

【Day 04】String Methods

前言 今天要来介绍 string Methods,可以把 string 进行各种处理,来做出你想做的...

欸! 我觉得自动化测试的架构应该长这样,测试应该这样写。

最近目前我的公司要做新的专案, 所以藉此需要一个新的专案来做自动化测试, 所以开始在思考一个好的自动...

[iT铁人赛Day28]练习题(7)

第二十八天了,讲到练习题第七题 不知不觉已经快结束了,因为篇幅的关系,所以可能无法说完全部的练习题 ...