如何去除代码中的if...else层层嵌套

手册/FAQ (369) 2016-04-07 10:08:10

 

首先来看问题代码:

  1. public static String query(){  

  2.         if(1==1){  

  3.             if(2==2){  

  4.                 if(3==3){  

  5.                     if(4==4){  

  6.                         int b=0;  

  7.                         for(int i=0;i<10000;i++){  

  8.                             if(i<10){  

  9.                                 continue;  

  10.                             }else{  

  11.                                 b+=i;  

  12.                                 return String.valueOf(b);  

  13.                             }  

  14.                         }  

  15.                     }else{  

  16.                         return "";  

  17.                     }  

  18.                 }else{  

  19.                     return "";  

  20.                 }  

  21.             }else{  

  22.                 return "";  

  23.             }  

  24.         }else{  

  25.             return "";  

  26.         }  

  27.         return "";  

  28.     }  

 

     其实我们会时常遇到这种逻辑上的嵌套判断,里面包含着各种循环,循环里面包含着小判断,刚开始的时候,代码还没有这么庞大,但是随着版本的迭代,后来的人很可能发现了这段代码有些逻辑上的小漏洞,于是就在这个基础上拼命加IF。。。else..最后搞得大家谁也不敢动这段代码,好像它一碰就会塌陷的样子。

 

     想到这个问题,是因为之前做过一个游戏的东西,本来就是个简单的抽奖逻辑,但是之后上线之前,PM大人让加上各种东西:比如,身份认证,线程安全,等待页面,活动未开始和活动已经结束处理等等。。。结果那个方法就神似了上面那个样子。

 

     今天写一段代码的时候,发现自己又陷入了各种if。。else嵌套,但是还好这次避开了这个坑:

 

  1. <span style="font-size:12px;">public static String query(Student stu) throws NoSuchMethodException,  

  2.             SecurityException, IllegalAccessException,  

  3.             IllegalArgumentException, InvocationTargetException {  

  4.         StringBuilder sb = new StringBuilder("select * from ");  

  5.         Class stuClass = stu.getClass();// 获取class  

  6.   

  7.         /* 如果没有加入table注解,返回null */  

  8.         if (!stuClass.isAnnotationPresent(Table.class)) {  

  9.             return null;  

  10.         }  

  11.         Table table = (Table) stuClass.getAnnotation(Table.class);// 获取到table注解  

  12.         sb.append(table.value() + " where 1=1 ");// 拼入表名称  

  13.         /* 通过get方法获取field字段值 */  

  14.         Field[] fields = stuClass.getDeclaredFields();// 获取类字段信息  

  15.         for (Field fd : fields) {  

  16.             if (!fd.isAnnotationPresent(Column.class)) {// 如果field未标记注解,不作为查询条件  

  17.                 continue;  

  18.             }  

  19.             String getMethodName = "get"  

  20.                     + fd.getName().substring(0, 1).toUpperCase()  

  21.                     + fd.getName().substring(1);  

  22.             Method getMethod = stuClass.getMethod(getMethodName); // 获取到field的get方法  

  23.             /* 如果函数动态调用返回值为空或者字段为integer未赋值,则不拼接 */  

  24.             if (getMethod.invoke(stu) == null  

  25.                     || (getMethod.invoke(stu) instanceof Integer && (Integer) getMethod  

  26.                             .invoke(stu) == 0)) {  

  27.                 continue;  

  28.             }  

  29.             if (getMethod.getReturnType() == String.class) {  

  30.                 sb.append("and " + fd.getName() + "='" + getMethod.invoke(stu)  

  31.                         + "'");  

  32.             } else if (getMethod.getReturnType() == int.class) {  

  33.                 sb.append("and " + fd.getName() + "=" + getMethod.invoke(stu));  

  34.             }// 其他类型自己判断去吧。。。但是感觉这么写不好。。。。有待改进的方法  

  35.   

  36.         }  

  37.   

  38.         return sb.toString();  

  39.     };  

  40. </span>  

  41.  
  42.  

           看出来了么,在if语句中,通过提前返回来减少if的嵌套,在for循环中,通过continue来提前结束本次循环。基本思路都是让代码以最自然,最流畅,自正常的思路进行下去,避免自己在看代码的时候也陷入自己挖的思维巨坑。

 

THE END