`
FansUnion
  • 浏览: 153329 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

读书笔记-编写可读代码的艺术[中]

 
阅读更多

观点:程序员之间的互相尊重体现在他所写的代码中。他们对工作的尊重也体现在那里。代码最重要的读者不是编译器,解释器或电脑,而是人。写出的代码能让人快速理解、轻松维护、容易扩展的程序员才是专业的程序员。

《编写可读代码的艺术》一书,专注于如何编写可读性更好的代码。

本文概要总结了这本书的第2部分内容。

第2部分 简化循环和逻辑

7.把控制流变得易读

关键思想:把条件、循环以及其它对控制流的改变做得越“自然”越好。运用一种方式使读者不用停下来重读你的代码。

7.1条件语句中参数的顺序

if(age >20){
}
比if(20 < age){
}
更易读。

if(name == null){
}
比
if(null == name){
}



在中文和英文等自然语言中(“如果你的年龄大于20”)更常见,更符合一般用法。
即比较的左侧,它的值倾向于不断变化,比较的右侧,它的值倾向于稳定。

7.2if/else语句块的顺序

if(a== b){
  //case one
}else{
  //case two
}
也可以写成
if(a != b){
  //case one
}else{
  //case two
}


之前你可能没想太多,但在有些情况下有理由相信其中一种顺序比另一种好:
a.首先处理正逻辑而不是负逻辑的情况。例如,if(debug)而不是if(!debug)。
b.先处理简单的情况。这种方式可能还会使得if和else在屏幕之内都可见,这很好。
c.先处理有趣的或者是可疑的情况。

下面所示是负逻辑更简单并且更有趣的一种情况,那么会先处理它

if (not the same  username){
  //case one
}else{
  //case two
}


7.3三目运算符
它对于可读性的影响是富有争议的。拥护者认为这种方式可以只写一行而不用写成多行,反对者则说
这可能会造成阅读的混乱而且很难用调试器来调试。

关键思想:相对于追求最小化代码行数,一个更好的度量方法是最小化人们理解它所需的时间。
建议:默认情况下都用if/else。三目运算符?:只有在最简单的情况下使用。

7.4避免do/while循环

do{

}while(condition);


do/while循环的奇怪之处是一个代码块是否会执行是由其后的一个条件决定的。通常来讲,逻辑条件
应该出现在它们“保护”的代码之前,这是if,while和for语句的工作方式。
因为你通常会从前向后来读代码,这使得do/while循环有点不自然了。

7.5从函数中提前返回

public boolean contains(String str,String substr){
  if(str==null || substr==null){
    return false;
  }
    
   if(substr.equals("")){
    return true;
    }
    
  ...
}


7.6最小化嵌套

if(userResult==SUCCESS){
  if(permissionResult != SUCCESS){
   reply.writeErrors("error reading permission");
   reply.done();
   return;
  }
  reply.writeErrors("");
}else{
  reply.writeErrors(userResult);
}
reply.done();


可以通过提前返回,来减少嵌套。


8.拆分超长的表达式
8.1用做解释的变量

if(line.split(",")[0].name=="root"){
 
 }
 
 增加一个解释变量
 String username = line.split(",")[0].name;
 if(name=="root"){
 }
 




8.2总结变量
即使一个表达式不需要变量(因为你可以看出它的含义),把它装入一个新变量中仍然有用。
我们把它叫做总结变量,因为它的目的是用一个短很多的名字来代替一大块代码,这个名字会
更容易思管理和思考。

if(request.user.id == document.user.id){
 //user can edit this document
}

if(request.user.id != document.user.id){
 //document is read only
}


这里的表达式“request.user.id==document.user.id”看上去可能并不长,但它包含
5个变量,所以需要多花点时间来想一想如何处理它。

这段代码中的主要概念是:“该用户拥有此文档吗?”这个概念可以通过增加一个总结变量来表达得更清楚。

final boolean userOwnDocument = (request.user.id==document.user.id);
if(userOwnDocument){...
}
if(!userOwnDocument){...
}



9.变量与可读性

关于变量的3个问题
a.变量越多,就越难全部跟踪它们的动向。
b.变量的作用域越大,就需要跟踪它的动向更久。
c.变量改变得越频繁,就越难以跟踪它的当前值。

9.1减少变量

没有价值的临时变量
now = datatime.time();
rootMessage.lastVisitTime=now;

减少控制流变量
boolean done=false;
if(condition && !done){
  if(...){
    done=true;
    continue;
  }
}

可以改为
if(condition){
  if(...){
    break;
  }
}


9.2缩小变量的作用域

把定义向下移
int a=0;
int b=0;
int c=0;

//handle a
//handle b
//handle c

改为
int a=0;
//handle a

int b=0
//handle b

全局变量改为局部变量。



9.3只写一次的变量更好

public static final int MAX_AGE=140;


原文链接:http://FansUnion.cn/articles/1903

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics