工程实践:如何给变量取一个好的名字

在上一篇文章中跟你们分享了关于函数命名的一些实践心得,今天咱们继续命名这个话题,来说一讲如何对变量命名。html

  如下是本文的目录大纲:java

  一. 变量命名风格bash

  二. 变量命名最高境界ide

  三. 变量命名最佳实践函数

  如有不正之处请多多谅解,并欢迎批评指正。优化

  请尊重做者劳动成果,转载请标明原文连接:this

 https://www.cnblogs.com/dolphin0520/p/10639167.htmlspa

一.变量命名风格

  变量命名风格一般会根据不一样的变量类型来区分,以Java语言为例,根据变量类型不一样有两种命名风格:代码规范

1)类成员变量、局部变量code

  类成员变量、局部变量一般采用驼峰命名风格,以下:

String userName;
复制代码

2)静态成员变量、枚举值、常量

  静态成员变量、枚举值、常量一般采用全部字母大写、多个单词以英文下划线链接,如:

public static final int MAX_YEARS = 25;
​
// 建议枚举类都以Enum结尾
enum ColorEnum {
    RED(0, "红色"),
    YELLOW(1, "黄色"),
    GREEN(2, "绿色"),
    WHITE(3, "白色"),
    BLACK(4, "黑色");
    private int code;
    private String name;
​
    Color(int code, String name) {
        this.code = code;
        this.name = name;
    }
}复制代码

二.变量命名最高境界

  在函数命名那篇中咱们说的函数命名最高境界是见字如面,那么对于变量命名来讲,最高境界是什么呢? 我认为是:自解释,即"代码即注释"。

  为何这么说呢,由于一般来讲一个函数是会有函数注释的,即便函数名字取的很差,若是注释写的比较清楚,对于后续维护人员来讲也是了解函数具体功能的一种方式。

  而变量则不一样,在一个工程里面,变量的数量远远大于函数的数量,因此不太可能对于每一个变量都去写注释,因此若是一个工程的变量命名很糟糕,那么对于后续维护人员来讲将是毁灭性的打击,由于每读到一个变量,可能就须要去猜想变量的含义,我想没有哪一个人愿意读到这样的代码,永远记住一点:"代码是写给人看的,不是写给机器看的"。

  譬以下面这段代码的命名就很是糟糕:

ppn = (cpn > 1) ? (cpn - 1) : cpn;
npn = (cpn < tpn) ? (cpn + 1) : tpn;
​
p = new Page(ppn, cpn, npn, tpn);复制代码

  上面这段代码估计只有原做者清楚地知道各个变量的含义是啥了,

  若是修改成下面这种写法,可读性会好不少,而且一目了然,很容易知道其大概意图是计算分页信息:

prePageNum = (curPageNum > 1) ? (curPageNum - 1) : curPageNum;
nextPageNum = (curPageNum < totalPageNum) ? (curPageNum + 1) : totalPageNum;
​
page = new Page(prePageNum, curPageNum, nextPageNum, totalPageNum);复制代码

三.变量命名最佳实践

1)采用名词或者形容词来命名变量

  变量通常状况下建议使用名词、名字组合或者形容词,由于变量通常形容的是一种事物或者事物的属性,因此用名词或者名词组合更容易让人理解,而形容词通常用于bool类型的变量。

2)避免使用单字母变量,尽可能细化变量含义

  在程序中,尽可能避免使用单字母变量,惟一能够接受使用单字母变量的场景只有for循环,不过仍是不太推荐在for循环中使用单字母变量(用pos、index比for循环的i、j、k要好不少)。

  举个例子,好比下面这行代码:

double calConeVolume(double b, double d) {
  return Math.PI * b * b * d / 3;
}复制代码

  咋一看这个函数参数感受挺清晰,可是一细看,b是什么?d又是什么?若是我要用这个函数,该怎么传参?估计大部人是一脸懵逼状,只能进去看实际的函数实现才知道b是圆锥体半径,d是圆锥体高度;

  那么怎么优化这段代码命名呢?其实很简单,稍微细化一下变量含义,让变量名本身去表达实际意图:

double calConeVolume(double radius, double height) {
  return Math.PI * radius * radius * height / 3;
}复制代码

3)变量命名先后用词需统一

  在同一个工程或者一个场景下,变量命名风格需先后统一,好比total和sum都能表示总计的意思,那么全部须要用到"总计"含义的地方要么所有使用total、要么所有使用sum。

  保持先后命名风格统一是保证工程代码良好可读性的关键保证。

4)集合变量用类型或者复数s做为后缀

  在java中,有不少集合,好比List、Map、Set等,那么集合变量该怎么命名呢?

  通常可采起两种方式:

  • 使用复数s结尾

List<Student> students = new ArrayList<>();
复制代码

  • 用集合类型做为后缀

List<Student> studentList = new ArrayList<>();
复制代码

  上面两种方式都可,没有比较明显的偏好,根据实际场景决定。第一种方式相对更简洁,第二种在局部做用域里面有多种相关的集合变量时区分度更大,好比:

List<Student> studentList = new ArrayList<>();
Map<Long, Student> studentMap = Maps.newHashMap();
​
for (Student stu : studentList) {
  studentMap.put(stu.getId, stu);
}复制代码

  个人建议是若是局部做用域只有一种类型的集合,那么推荐使用复数形式;若是局部做用域有多个相关的集合类型,那么推荐用类型结尾。

5)禁止使用is做为bool类型的类成员变量前置

  在java中,禁止用is做为bool类型的类成员变量的前缀,由于is做为前缀会致使序列化/反序列出现问题,阿里的java代码规范中也明确提到了这一点,因此在写代码的时候最好仍是遵照公认的规范,否则哪天说不定就踩坑了。

6)尽可能避免使用缩写进行命名

  有些时候,变量名可能有点长,不利于代码可读性,所以不少时候在写代码的时候喜欢用缩写来命名,但这个不是一个好的习惯,除非使用的缩写是你们都会使用的约定俗称的缩写。

  好比下面这个命名:

int avgStudentAge;
复制代码

  由于avg你们都知道是average的缩写,因此这么写问题不大,不会引发歧义;

  可是下面这种缩写命名:

res
tmp
cnt
dep复制代码

  就不是好的缩写命名,由于不一样的人阅读可能会有不一样的理解:

res => response、resource、result
tmp => temporary、template
cnt => count、content、context复制代码

  附上一些约定俗称的缩写:

全称 缩写
identification id
average avg
maximum max
minimum min
buffer buf
error err
message msg
image img
length len
library lib
password pwd
position pos
data transfer object dto
view object vo

7)抛弃掉flag变量

  国内一些早期的教材上,处处充斥着各类flag风格的变量,这种命名方式对于大型工程简直就是噩梦,好比:

int flag = getDoctorFlag(doctorId);
if (flag == 1) {
  //....
}复制代码

  看到这段代码,读者会有疑问flag变量的含义是什么?flag值为1的时候又表明什么含义?是医生的值班/在岗状态、仍是医生的身体状态?估计读者的心里是崩溃的。

  若是优化成下面这种形式:

DutyStatus doctorDutyStatus = getDoctorDutyStatus(doctorId);
if (doctorDutyStatus == DutyStatus.ONLINE) {
  // ...
}复制代码

  就比上面的形式清晰多了,很容易看出来判断的是医生的值班/在岗状态。


博客园连接:https://www.cnblogs.com/dolphin0520/

公众号:

相关文章
相关标签/搜索