如何评价代码质量?

代码质量的评价有很强的主观性

最常用的评价标准有可维护性、可读性、、可扩展性、灵活性、简洁性、可复用性、可测试性。

一、可维护性

我们先来看看几个概念

维护:是指修改bug、修改捞的代码、添加新的代码之类的工作;

代码易维护:指不破坏原有代码设计、不引入新的 bug 的情况下,能够快速地修改或者添加代码;

代码不易维护:指修改或者添加代码需要冒着极大的引入新 bug 的风险,并且需要花费很长的时间才能完成。

我们可以从侧面上给出一个比较直观但又比较准确的感受。

如果 bug 容易修复、修改、添加功能也能轻松完成,那我们就可以主观的认为代码对我们来说是易维护的。

是否易维护本来就是针对维护的人来说的,不同水平的人对于同一份代码的维护能力也是不相同的,而且对系统的熟悉程度也占很大的主观因素。

二、可读性

如何评价一段代码的可读性呢?

很难给出一个覆盖所有评价指标的列表,比如是否符合编码规范、命名是否达意、注释是否详尽、函数是否长短合适、模块是否清晰、是否符合高内聚低耦合等等。

实际上,code review 是一个很好的检测代码可读性的手段。如果别人可以轻松读懂你写的代码,那说明你的代码可读性很好;如果同事读你的代码时,有很多疑问,那就说明你的代码可读性有待提高了。

三、可扩展性

在不修改或少量修改原有代码的情况下,通过扩展的方式添加新的功能代码。

说直白点就是,代码预留了一些功能扩展点,你可以把新功能代码,直接插到扩展点上,而不需要一位添加一个功能而大东干戈,改动大量的原始代码。

开闭原则

添加一个新的功能,应该是通过在已有代码基础上扩展代码(新增模块、类、方法、属性等),而非修改已有代码(修改模块、类、方法、属性等)的方式来完成。

关于定义,我们有两点要注意。第一点是,开闭原则并不是说完全杜绝修改,而是以最小的修改代码的代价来完成新功能的开发。第二点是,同样的代码改动,在粗代码粒度下,可能被认定为“修改”;在细代码粒度下,可能又被认定为“扩展”。

四、灵活性

灵活这个词的含义非常宽泛,很多场景下都可以使用功能。如果一段代码易扩展、易复用或者易用,都可以称字段代码写得比较灵活

五、简洁性

KISS 原则:“Keep It Simple, Stupid” 。尽量保持代码简单。

KISS 原则是保持代码可读和可维护的重要手段。KISS 原则中的“简单”并不是以代码行数来考量的。代码行数越少并不代表代码越简单,我们还要考虑逻辑复杂度、实现难度、代码的可读性等。而且,本身就复杂的问题,用复杂的方法解决,并不违背 KISS 原则。除此之外,同样的代码,在某个业务场景下满足 KISS 原则,换一个应用场景可能就不满足了。

KISS原则

对于如何写出满足 KISS 原则的代码,有几条指导原则:

  • 不要使用同事可能不懂的技术来实现代码;
  • 不要重复造轮子,要善于使用已经有的工具类库;
  • 不要过度优化。

六、可复用性

可以简单地理解为,尽量减少重复代码的编写。

代码可复用性和 DRY (Don't Repeat Yourself/不要重复自己)这条设计原则的关系挺紧密的。

DRY原则

三种代码重复的情况:实现逻辑重复、功能语义重复、代码执行重复

  • 实现逻辑重复,但功能语义不重复的代码,并不违反 DRY 原则。
  • 实现逻辑不重复,但功能语义重复的代码,也算是违反 DRY 原则。
  • 除此之外,代码执行重复也算是违反 DRY 原则。

提高代码可复用性的一些方法,有以下 7 点。

  • 减少代码耦合
  • 满足单一职责原则
  • 模块化
  • 业务与非业务逻辑分离
  • 通用代码下沉
  • 继承、多态、抽象、封装
  • 应用模板等设计模式

七、可测试性

代码可测试性的好坏,能从侧面上非常准确地反应代码质量的好坏。

代码的可测试差,比较难写单元测试,那基本上就能说明代码设计得有问题。

1. 什么是代码的可测试性?

粗略地讲,所谓代码的可测试性,就是针对代码编写单元测试的难易程度。对于一段代码,如果很难为其编写单元测试,或者单元测试写起来很费劲,需要依靠单元测试框架中很高级的特性,那往往就意味着代码设计得不够合理,代码的可测试性不好。

2. 编写可测试性代码的最有效手段

依赖注入是编写可测试性代码的最有效手段。通过依赖注入,我们在编写单元测试的时候,可以通过mock(模拟)的方法解依赖外部服务,这也是我们在编写单元测试的过程中最有技术挑战的地方。

3. 常见的 Anti-Patterns(反面模式)

常见的测试不友好的代码有下面这 5 种:

  • 代码中包含未决行为逻辑(所谓的未决行为逻辑就是,代码的输出是随机或者说不确定的,比如,跟时间、随机数有关的代码。)
  • 滥用可变全局变量
  • 滥用静态方法
  • 使用复杂的继承关系
  • 高度耦合的代码

猜你喜欢

转载自juejin.im/post/7016228607349506078