【问题标题】:Is this code correct for overloading comparision operator?此代码对于重载比较运算符是否正确?
【发布时间】:2016-08-19 18:52:32
【问题描述】:

以下代码对于重载比较运算符是否正确?这段代码中是否有任何愚蠢的错误或循环漏洞?我特别怀疑 if 循环 if (b1 == b2)if (&b1 == &b2)?哪一个是正确的,最终通过引用吧,我想。如果我们在堆上分配对象,我们可以比较指针吗?

代码如下:

#include <QCoreApplication>
#include <iostream>

using namespace std;

class Base{
private:
    //static const int i=10;
    int j;
    string str;
public:
    //void display() const;
    //int read();
    bool operator==(const Base &rhs);
};

bool Base::operator ==(const Base &rhs)
{
    if((this->j == rhs.j) && (this->str == rhs.str))
        return true;
    else
        return false;
}

int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);
    Base b1, b2;
    if(&b1 == &b2) // or if(b1 == b2)
    {
        cout << "Equal\n";
    }
    else
    {
        cout << "Not equal\n";
    }
    return a.exec();
}

【问题讨论】:

    标签: c++ operator-overloading pass-by-reference


    【解决方案1】:

    这个函数签名告诉编译器比较操作符可以改变对象的值,所以它不能在 const 对象上调用。所以最好将其声明为 const:

    bool operator==(const Base &rhs) const;
    

    在这段代码中,您正在比较两个对象的地址:

    if(&b1 == &b2) // or if(b1 == b2)
    {
        cout << "Equal\n";
    }
    else
    {
        cout << "Not equal\n";
    }
    

    它们显然不相等。 if (b1 == b2) { ... } 如果要检查对象是否相等,则正确。

    如果我们在堆上分配对象,我们可以比较指针吗?

    如果 a 和 b 是指针,您可以将指针值比较为:

    *a == *b 
    

    或显式调用 operator==(什么是丑陋的):

    a->operator==(*b)
    

    在 c++ 中将此类运算符声明为朋友是很常见的(但在您的情况下,这不是必需的)。在此代码中使用 this 也不会提高可读性。我希望将此运算符视为:

    bool Base::operator == (const Base & rhs) const
    {
        return j == rsh.j and str == rhs.str;
    }
    

    作为一般说明,由于该类称为 Base 可能您可能还需要将其声明为虚拟。

    添加:在这种情况下,j 也不会被初始化。修复它的最简单方法是将初始化程序添加到声明中:

    class Base {
    private:
        int j = 0;
        string str;
    // ...
    };
    

    【讨论】:

    • 在任何一种情况下,我都会变得不相等。如果内容相同,那么相等应该返回true吧?
    • 在您的情况下,您正在比较两个未初始化的对象。所以如果string默认初始化为空,那么i每次都会被垃圾初始化。
    • 是的,我明白你的意思,如果我注释 int 和 string,并且只比较静态 const,那么这两个对象是相等的。
    • 感谢您的评论,我已经编辑了答案以添加示例如何在没有构造函数的情况下初始化 j。
    【解决方案2】:

    比较运算符逻辑看起来是正确的,但是

    1. 您缺少const

      bool operator==(const Base &rhs) const;
      

      这是您向编译器做出的承诺,即您的操作员不会修改调用它的实例;没有它,您的运算符将无法用于左侧为const 的比较。

    2. 当然它不是由行调用的

      if(&b1 == &b2) 
      

      因为这里您正在比较指针,这些指针已经具有比较运算符(如果两个指针指向同一个实例,则返回 true)。实际调用运算符的正确方法是直接比较对象,例如

      if(b1 == b2)
      

    【讨论】:

      【解决方案3】:

      发布的代码是比较基础对象的内存地址。此 if 语句将始终在 b1 和 b2 之间比较 false,除非 b1 是 b2。

      【讨论】:

        【解决方案4】:

        根据当前的实现,进行以下更改 将(&amp;b1 == &amp;b2) 替换为(b1 == b2),你的代码就可以正常工作了

        (&amp;b1 == &amp;b2) => 比较地址,不可能相同。 (b1 == b2) => 比较内容。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2020-02-25
          相关资源
          最近更新 更多