文档章节

Android代码重构总结

叶大侠
 叶大侠
发布于 2017/08/02 22:12
字数 1769
阅读 23
收藏 0

这个总结比较晚了,快相隔一年了,总想挤点什么出来写一下,一方面是避免让自己懒下来,另一方面也是迫使自己复盘,思考这个过程中哪些地方做得还Ok,哪些地方做的不好。

不少公司初期的项目为了快速和低成本开发产品,一开始可能会找外包或者开发能力一般的开发人员来完成,等公司业务上去了,这时候也欠了一屁股的技术债,很幸运,我刚好就当了一回接盘侠。

初接手项目,闻到坏代码的味道,不要急于作出改变,重构是一件需要小心翼翼进行的一件事情,你的每一点改动都会给QA的童鞋带来额外的工作量,尽管你觉得没有问题。所以,第一步要做的就是先把整体的情况先摸个底,先把问题暴露出来,制定好你初步的重构方案。在这个过程中,你可能要先默默的利用空闲时间做好方案,毕竟可能还有很多业务代码要写的,你不得不忍受先在原来的框架上把当前的工作完成。

在我审视整个项目的时候,我发现存在有如下的问题:

  1. 多个已经不在维护的第三方库,尤其是网络库,没有进行二次封装,耦合度非常高;
  2. sdk版本也近一年没有进行更新过;
  3. 一些库使用方法不恰当,可能会带来内存泄漏和组件状态不正确(比如所在的 Activity 已经销毁)导致的崩溃问题;
  4. 有不少重复性很高的代码散落在各处;
  5. 变量名和方法名有些随意,驼峰和下划线风格并存;
  6. 逻辑过于冗长的方法,比如和 H5 页面的协议处理,近 1K 行的 if else
  7. 没有考虑一些边界条件,比如请求失败重试,没有数据的情况;
  8. 存在不少的魔数,往往在一些关键的逻辑里面,涉及到很多状态的变化处理。
  9. 没有懒加载用户还不需要的资源,页面 overdraw 的情况严重等;
  10. 还有一些情况暂时回想不起来,总之情况比较恶劣,骂人的冲动都有。

整理好问题和写好初步的重构方案之后,接下来就可以找你的老大去聊这个事情了,一般来说都会得到支持,这样也可以让上面知道你在埋头苦干的时候是在干嘛,当时的想法是想推翻重建的,做法就是一个新的项目工程和一个旧的并行开发,有新的开发任务就先在旧的工程上开发,然后新的工程就逐步赶上和替代,最后一次性把新的 app 交付给 QA 进行一次从头到尾的测试,当时评估这样应该会比在原来的基础上改耗费的时间要更少一些。但很快发现这样做行不通,一方面需求在不断变化,引起的变化两边工程都要改动;另外在开发进度上会和 iOS 端很难同步。所以很快不得改变了思路,整合新旧的代码,然后在同一条工程线上进行重构,这样一来,必然就多了很多整合的工作,重构变成了一个抽丝剥茧的过程,没那么痛快了,但好处就是每一步做的工作,都可以被看见。

既然是想改善代码,那肯定要先阻断烂代码再被添加进来,因此,第一件事要先建立起代码的相关规范,有可能的话,要尽可能加入 Code Review 这一流程来驱动规范的落实。重构的思路是从底层往高层,从变化少到变化频繁,比如底层的网络请求、图片缓存处理,这是变化少的部分,而页面和相关逻辑就是变化频繁的部分,从底层到高层好理解,从变化少到变化多则是对应经常变化的需求,或许在下个版本你就可以顺便把它重新做一遍,原来的代码彻底删除掉了。这里分享一部分具体的做法,可能对你有启发:

  1. 在改写网络层的时候,这次通过策略模式来分离了网络请求过程和数据解析过程,这样不管以后是用 okhttp 还是 volley ,是 Json 还是 Protocol Buffers 结构的数据,喜欢用 gson 还是 fastjson , 都只需要修改少量的代码,而且对上层调用没有任何影响。另外,由于新和旧的网络库不一样,为了减少 jar 包的数量,决定对旧的接口进行完全的兼容,但底层用的还是新的网络库。改写这一层后,对于新的代码就用新的接口,以前的就可以等待合适的时机再进行替换了。
  2. 这个 app 很多混合开发的地方,很多 H5 页面的点击需要调用起原生的方法,由于自定义的跳转协议数量非常多,原来的处理方法已经超过近 1K 行的代码,这样必然导致阅读和修改困难的问题,这里我采用了大家熟悉的状态模式把相关职责分散到不同的类里面了。
  3. 很多页面都有相似的过程,比如从从数据加载到加载失败处理,刷新和加载更多等,这些可以通过模板方法把相关的逻辑封装到基类里面,然后让子类去实现变化的部分,比如不同的视图和数据的绑定,可以大大减少代码量。

还有一些技巧已经回忆不起来了,整个重构过程的彻底完成花了差不多半年的时间,期间经历了好几个版本的迭代。从效果来看,重构后带来的好处是显著的:首先提升了今后的开发效率,拥有了更好的可维护性,其次 bug 的数量和崩溃率也有了大幅度的好转,最后得益于各种库的升级和优化,app 的性能也得到了不少的提升。总结一下,重构是一件春天播种,秋天收获的事情,要有耐心;正确的方法很重要,循序渐进可能比推翻重来更科学。

广告时间:建了个群,和大家业余探讨如何用技术去创收,有兴趣的童鞋可以加一下:

© 著作权归作者所有

共有 人打赏支持
叶大侠

叶大侠

粉丝 58
博文 44
码字总数 67312
作品 5
广州
程序员
私信 提问
SimpleNews 项目的重构之旅(5) - Android Gradle 打包&混淆应用

应用场景 之前一直没有做 Android APK 发包管理,所以这次重构把这打包这部分考虑进去,之后可能会发布到一些应用市场。 要实现的功能 混淆代码 实现签名 过滤无用资源 生成 release 版本 AP...

無名小子的杂货铺
2017/06/12
0
0
SimpleNews 项目的重构之旅(4) -Gradle for Android 基础知识汇总

Gradle 使用 Android Studio 都知道 Gradle,在 SimpleNews 项目中,前期的时候并不是很了解 Gradle 语法等,只是使用 Android Studio 默认的配置来构建,后续也只是关注在功能方向,没有过多...

無名小子的杂货铺
2017/06/03
0
0
SimpleNews 项目的重构之旅(3) -EventBus 接入

通过需求使用 EventBus 之前就接触过 EventBus ,只是没有在项目中使用过,练习地址 WPEventBusDemo ,今天在项目中接入 EventBus 。 最开始的目的是为了做一个完全退出机制,看了网上很多用...

無名小子的杂货铺
2017/06/02
0
0
关于Android MVP模式的思考

这一周对现有的Android项目进行了框架重构,使用MVP模式来重新构建整个项目和包结构。今天就来总结一下我在这个过程中理解和实践吧。 MVP概述 MVP是指Model,View和Presenter的缩写,是MVC模...

carpediem123
2017/03/12
0
0
Android APP用Kotlin重构

Android代码重构,原先JAVA代码比较简单的实现,没有很好的规划。软件只有一个主功能,类似POS机。 代码量大概2000~2500行。 希望使用完善的MVP/MVC设计模式重构,去耦合。 还需要包含完善的...

stopkill
2017/06/08
0
0

没有更多内容

加载失败,请刷新页面

加载更多

微服务分布式事务实现

https://www.processon.com/view/link/5b2144d7e4b001a14d3d2d30

WALK_MAN
17分钟前
0
0
《大漠烟尘》读书笔记及读后感文章3700字

《大漠烟尘》读书笔记及读后感文章3700字: 在这个浮躁的社会里,你有多久没有好好读完一本书了? 我们总觉得自己和别人不一样,所以当看到别人身上的问题时,很少有“反求诸己”,反思自己。...

原创小博客
52分钟前
1
0
大数据教程(9.5)用MR实现sql中的jion逻辑

上一篇博客讲解了使用jar -jar的方式来运行提交MR程序,以及通过修改YarnRunner的源码来实现MR的windows开发环境提交到集群的方式。本篇博主将分享sql中常见的join操作。 一、需求 订单数据表...

em_aaron
今天
1
0
十万个为什么之什么是resultful规范

起源 越来越多的人开始意识到,网站即软件,而且是一种新型的软件。这种"互联网软件"采用客户端/服务器模式,建立在分布式体系上,通过互联网通信,具有高延时(high latency)、高并发等特点...

尾生
今天
1
0
Terraform配置文件(Terraform configuration)

Terraform配置文件 翻译自Terraform Configuration Terraform用文本文件来描述设备、设置变量。这些文件被称为Terraform配置文件,以.tf结尾。这一部分将讲述Terraform配置文件的加载与格式。...

buddie
今天
2
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部