Pulpcode

捕获,搅碎,拼接,吞咽

0%

关于If的几种写法

好吧,我其实也不知道自己为什么要写这么一篇Blog。有的时候我都怀疑自己是不是处女座的。虽然我不信星座这种东西,同时我也觉得星座也就能用来骗骗妹子。
可是每每当自己在写 if语句 和看到一些同事写的 很糟糕的if语句 时,我就忍不住去想:怎样写才好?

目录

if … if 和 if … else if … else if … else

这其实并不是写法的问题,其实我发现真的有人会把该用 if ... else if ... else if ... else 的地方写成 if ... if。表面上看起来没问题,其实他们确实是误打误撞,当出错的时候原因是什么都不知道。

首先请看下面两段代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
// if ... if 形式
if(a == 5)
{
cout << "FIVE";
}

if(a == 6){
cout << "SIX";
}

if(a == 7)
{
cout << "SEVEN";
}

// if ... else if ... else if ... else 形式
if( a == 5)
{
cout << "FIVE";

}else if( a == 6)
{
cout << "SIX";
}else if( a == 7 )
{
cout << "SEVEN";
}

这两断代码执行起来是一样的,为什么?因为它们 判断的条件自身是互斥的 ,a只能等于这些数中的一个,等于5就不能等于6了,所以也确实没什么问题。

但是下面两段代码就不同了。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
// if ... if 形式
if(a < 3)
{
cout << "less than Three";
}

if(a < 5)
{
cout << "less than Five";
}

if(a < 7)
{
cout << "less than Seven";
}

// if ... else if ... else if ... else 形式
if(a < 3)
{
cout << "less than Three ";
}else if(a < 5)
{
cout << "less than Five and greater than or equal Three";
}else if(a < 7)
{
cout << "less than Seven and greater than or equal Five";
}

所以一些人的if语句会产生bug,就是把本应该 相互关联的条件分开判断 了。
他们在发现自己的代码不能按照期望执行时往往会用加断点进行调试,然后查看自己的代码是否执行正常,最后常常发现一些不应该执行if语句的被执行了。
而且有些人并没有发现 if ... else if ... else if ... else 本身是互斥,还在写这种代码:

1
2
3
4
5
6
7
8
9
10
if(a < 3)
{
cout << "less than Three ";
}else if(3<=a && a<5)
{
cout << "less than Five and greater than or equal Three";
}else if(5<=a && a<7)
{
cout << "less than Seven and greater than or equal Five";
}

它们是关联的if,只会执行其中的一个,所以你多余的判断,根本没必要。

多余判断还算好,更要命的是如果你在代码中还修改了条件变量的值。

比如如下代码:

1
2
3
4
5
6
7
8

if(a > 3){
a = 0;
}

if (a<=3){
a++;
}

代码本来是判断a是否大于3如果是就归零,否则自增。可惜因为条件并不是互斥的,所以结果在归零后 ,马上又执行了下面的语句。

下面的这种写法会好很多:

1
2
3
4
5
6

if(a > 3){
a = 0;
}else if (a<=3){
a++;
}

所以我的建议就是:如果你在判断一个互斥条件,那么既然这些条件是相互关联的,就应该用 if ... else if ... 连起来。
尤其是判断对象是否等于某个值,这种能用switch写的东西,用 if ... else lf ... 写其实挺好的。当然如果是选择的数量比较多时,用switch才会更好些。

比如我最近写的一段代码要判读拥有某些职位的人是否存在,存在的话就加到队列里发消息。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
messageSeq = new List<Employee>();

if(zhuren != null)
{
seq.add(zhuren);
}

if(fuzhuren != null)
{
seq.add(fuzhuren);
}

if(yuanzhang != null)
{
seq.add(fuzhuren);
}

看!这些if之间本身并没有“任何关系”。

if … if 和 if … else if … else if … else 总结

  • if ... else if ... else if ... else 这样的写法,if条件之间是存在某种关系的,而且这些关系是互斥的,也就是说它们之中只能有一个执行。
  • if ... if 是两段“毫无关系”的代码,只不过被你写的近而已。

if … else 和三元运算符

其实有的时候,它们真的在表达一个东西:

看下面两段代码,将a和b中较大的赋给max

1
2
3
4
5
6
7
8
if(a > b)
{
max = a;
}
else
{
max = b;
}

1
max = a>b ? a:b;

你要问我有什么区别,我现在的水平只能告诉你,if...else 是在执行一些语句,而三元运算符却是个能够返回值的表达式。所以只有是在赋值,或者其它一些能够返回值的代码,这两种写法都行,而且三元运算符写起来确实很短小精悍。
但是当你要通过if条件判断去执行一些do something的语句时,你确实不得不用 if ... else

1
2
3
4
5
6
7
8
if(con)
{
dosomething();
}
else
{
dootherthing();
}

return 的 if

我发现不仅仅是我,在读王垠大神的博客时,发现他也想过这个问题。

1
2
3
4
5
if(con)
{
return True;
}
return False;

有的人(比如王垠大神)就是纠结应该写成这样:

1
2
3
4
5
6
7
8
if(con)
{
return True;
}
else
{
return False;
}

我觉得还是第一种好,为什么?

  1. 第一种短
  2. 大多数程序员都用第一种写法
  3. 其实有的很长的函数在最开始处判断条件不符合直接就return了
1
2
3
4
5
6
7
8
9
if(prject == null)
{
return ;
}
// 很多很复杂的代码
xxx;
xxx;
xxx;
xxx;

你觉得你配个else再加缩进会好看么?

else处女座最后的纠结

其实还有一点纠结的事,就是这个else这个东西。
if ... else 看上去像是“平起平坐”的两种线,只不过else里面不用写条件了。其实我觉得根本不是那样。

else其实真的就在 if ... else if ... else ... 的最后面,就像是switch的default。
而且python的for语句是可以接else的,其作用是在for循环中,如果没有从任何一个break中退出,则会执行for后面的else。

1
2
3
4
5
for i in seq:
if i == 5:
break
else:
print "not has five"

所以你可以这样理解else:它真的就是来做”收尾”工作的。

这就是我对if的理解。BTW,我是水瓶座的…