第38课 逻辑操作符的陷阱

潜规则:

在C语言中并没有bool类型。C++中才有。

逻辑表达式示例:

添加func函数:

 1 #include <iostream>
 2 #include <string>
 3 
 4 using namespace std;
 5 
 6 int func(int i)
 7 {
 8     cout << "int func(int i) : i = " << i << endl;
 9     
10     return i;
11 }
12 
13 int main()
14 {
15     if( func(0) && func(1) )
16     {
17         cout << "Result is true!" << endl;
18     }
19     else
20     {
21         cout << "Result is false!" << endl;
22     }
23     
24     cout << endl;
25     
26     if( func(0) || func(1) )
27     {
28         cout << "Result is true!" << endl;
29     }
30     else
31     {
32         cout << "Result is false!" << endl;
33     }
34     
35     return 0;
36 }

 运行结果:

 重载逻辑操作符:

C++中允许重载逻辑与和逻辑或,重载逻辑操作符程序入下:

第42行我们期望只调用func(t0),但是从输出可以看到func(t1)也被调用了。而且先调用的是func(t1)。

继续演示:

 1 #include <iostream>
 2 #include <string>
 3 
 4 using namespace std;
 5 
 6 class Test
 7 {
 8     int mValue;
 9 public:
10     Test(int v)
11     {
12         mValue = v;
13     }
14     int value() const
15     {
16         return mValue;
17     }
18 };
19 
20 bool operator && (const Test& l, const Test& r)
21 {
22     return l.value() && r.value();
23 }
24 
25 bool operator || (const Test& l, const Test& r)
26 {
27     return l.value() || r.value();
28 }
29 
30 Test func(Test i)
31 {
32     cout << "Test func(Test i) : i.value() = " << i.value() << endl;
33     
34     return i;
35 }
36 
37 int main()
38 {
39     Test t0(0);
40     Test t1(1);
41     
42     if( func(t0) && func(t1) )
43     {
44         cout << "Result is true!" << endl;
45     }
46     else
47     {
48         cout << "Result is false!" << endl;
49     }
50     
51     cout << endl;
52     
53     if( func(1) || func(0) )
54     {
55         cout << "Result is true!" << endl;
56     }
57     else
58     {
59         cout << "Result is false!" << endl;
60     }
61     
62     return 0;
63 }

 运行结果如下:

 可以看到逻辑或也调用了两次,而且是先调用的func(0)。变成从右向左开始计算了。逻辑操作符本应从左向右计算。

问题的本质分析:

我们将&&和||换成函数调用的方式就容易理解了,这也是操作符重载的本质。

运行结果如下:

可以看到跟直接使用操作符的方式是一样的。

工程中最好不要重载逻辑与和逻辑或,因为不再满足短路规则。

逻辑操作符在重载后无法实现原生的语义。

建议:

 通过重载比较操作符,使一个对象和true或者false去比较,这样也可以实现需求。

小结:

原文地址:https://www.cnblogs.com/wanmeishenghuo/p/9573751.html