C++超详细讲解逻辑操作符

 更新时间:2022年06月01日 08:39:16   作者:清风自在 流水潺潺  
在C语言中,逻辑运算符有&&、||、!;&&表示“与”的意思,需要两端的表达式的值都为true,该式的值才为true。||表示“或”的意思,两端的表达式的值只要有一端为true,该式的值就为true。!表示“非”的意思,将该式的真值换成相反的真值,即false和true互换

一、逻辑运算符的原生语义

  1. 操作数只有两种值( true和 false )逻
  2. 辑表达式不用完全计算就能确定最终值
  3. 最终结果只能是 true 或者 false

下面看一个逻辑表达式的代码:

#include <iostream>
#include <string>
using namespace std;
int func(int i)
{
    cout << "int func(int i): i = " << i << endl;
    return i;
}
int main()
{
    if (func(0) && func(1))
    {
        cout << "Result is true!" << endl;
    }
    else 
    {
        cout << "Result is False!" << endl;
    }
    cout << endl;
    if (func(0) || func(1))
    {
        cout << "Result is true!" << endl;
    }
    else 
    {
        cout << "Result is False!" << endl;
    } 
    return 0;
}

输出结果如下:

这就是逻辑操作符的短路规则,可以参照我之前写的详细讲解逻辑运算符的使用

二、重载逻辑操作符

逻辑操作符可以重载吗?重载逻辑操作符有什么意义?

下面看一个重载逻辑操作符示例:

#include <iostream>
using namespace std;
class Test
{
    int mValue;
public:
    Test(int v)
    {
        mValue = v;
    }
    int value() const
    {
        return mValue;
    }
};
bool operator &&(const Test& l, const Test& r)
{
    return l.value() && r.value();
}
bool operator ||(const Test& l, const Test& r)
{
    return l.value() || r.value();
}
Test func(Test i)
{
    cout << "Test func(Test i): i.value() = " << i.value() << endl;
    return i;
}
int main()
{
    Test t0(0);
    Test t1(1);
    if (func(t0) && func(t1))
    {
        cout << "Result is true!" << endl;
    }
    else
    {
        cout << "Result is false!" << endl;
    }
    cout << endl;
    if (func(t0) || func(t1))
    {
        cout << "Result is true!" << endl;
    }
    else
    {
        cout << "Result is false!" << endl;
    }
}

输出结果如下:

按照短路法则,func(t0) && func(t1) 应该只执行 func(t0),这里却输出了func(t0) 和 func(t1) 运行后的值,这是为什么呢?且看下面解析。

问题的本质分析

  1. C++ 通过函数调用扩展操作符的功能
  2. 进入函数体前必须完成所有参数的计算
  3. 函数参数的计算次序是不定的
  4. 短路法则完全失效

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

上述代码等效写法如下:

#include <iostream>
using namespace std;
class Test
{
    int mValue;
public:
    Test(int v)
    {
        mValue = v;
    }
    int value() const
    {
        return mValue;
    }
};
bool operator &&(const Test& l, const Test& r)
{
    return l.value() && r.value();
}
bool operator ||(const Test& l, const Test& r)
{
    return l.value() || r.value();
}
Test func(Test i)
{
    cout << "Test func(Test i): i.value() = " << i.value() << endl;
    return i;
}
int main()
{
    Test t0(0);
    Test t1(1);
    if (operator && (func(t0), func(t1)))
    {
        cout << "Result is true!" << endl;
    }
    else
    {
        cout << "Result is false!" << endl;
    }
    cout << endl;
    if (operator || (func(t0), func(t1)))
    {
        cout << "Result is true!" << endl;
    }
    else
    {
        cout << "Result is false!" << endl;
    }
}

输出结果和上面一样:

将func(t0) && func(t1) 改写成operator && (func(t0), func(t1)),就不难理解为什么了。核心就两点:

1.进入函数体前必须完成所有参数的计算

2.函数参数的计算次序是不定的

一些有用的建议

  • 实际工程开发中避免重载逻辑操作符
  • 通过重载比较操作符代替逻辑操作符重载
  • 直接使用成员函数代替逻辑操作符重载
  • 使用全局函数对逻辑操作符进行重载

三、小结

  • C++ 从语法上支持逻辑操作符重载
  • 重载后的逻辑操作符不满足短路法则
  • 工程开发中不要重载逻辑操作符
  • 通过重载比较操作符替换逻辑操作符重载
  • 通过专用成员函数替换逻辑操作符重载

到此这篇关于C++超详细讲解逻辑操作符的文章就介绍到这了,更多相关C++逻辑操作符内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • C++第11版本中的一些强大的新特性小结

    C++第11版本中的一些强大的新特性小结

    这篇文章主要介绍了C++第11版本中的一些强大的新特性小结,需要的朋友可以参考下
    2015-12-12
  • C语言实现万年历

    C语言实现万年历

    这篇文章主要为大家详细介绍了C语言实现万年历,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2019-10-10
  • 关于大小端、位域的一些概念详解

    关于大小端、位域的一些概念详解

    我们常用的x86结构都是小端模式,而大部分DSP,ARM也是小端模式,不过有些ARM是可以选择大小端模式。所以对于上面的maxHeight是应该以小端模式来存放,具体情况请看下面两表
    2013-10-10
  • C++ 回调接口设计和二进制兼容详细

    C++ 回调接口设计和二进制兼容详细

    再开发视频编辑 SDK,SDK的回调接口设计成 C 风格,结构中放着一些函数指针,既然对外接口是 C++,为什么不直接使用 C++ 的虚函数?这篇文章便对这一问题做个详细介绍,需要的朋友可以参考一下
    2021-09-09
  • C++如何实现BCD码和ASCII码的相互转换

    C++如何实现BCD码和ASCII码的相互转换

    这篇文章主要介绍了C++实现BCD码和ASCII码互转,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-06-06
  • Matlab实现将图像序列合并为视频的方法详解

    Matlab实现将图像序列合并为视频的方法详解

    MATLAB是一种高性能语言,用于操纵矩阵、执行技术计算、绘图等。它代表矩阵实验室。借助这个软件,我们可以从图像中创建视频。这篇文章主要介绍了Matlab实现将图像序列合并为视频的四个方法,希望对大家有所帮助
    2023-03-03
  • C语言版医院管理系统

    C语言版医院管理系统

    这篇文章主要为大家详细介绍了C语言版医院管理系统,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2019-01-01
  • 浅谈关于C语言中#define的副作用

    浅谈关于C语言中#define的副作用

    这篇文章主要介绍了关于C语言中#define的副作用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2019-03-03
  • C++面向对象语言自制多级菜单功能实现代码

    C++面向对象语言自制多级菜单功能实现代码

    菜单类主要负责菜单的创建、修改、删除,是包含菜单结构组织和响应函数的模型,用户拥有充分的自主性,可根据需要自定义菜单显示和响应函数,这篇文章主要介绍了C++面向对象语言自制多级菜单,需要的朋友可以参考下
    2024-06-06
  • C++中int main(int argc, char** argv)的参数使用

    C++中int main(int argc, char** argv)的参数使用

    int main(int argc, char** argv) 是C和C++程序的入口点,其中argc和argv是用来接收从命令行传递给程序的参数的,本文就来介绍一下这两个参数的含义,感兴趣的可以了解一下的相关资料
    2024-01-01

最新评论