如何重载运算符==

How to overload operator ==?

本文关键字:运算符 重载 何重载      更新时间:2023-10-16

我有A级如何使操作员过载==执行

A a,b,c;
if (a==b==c) {}

有人能帮我吗?

非常简短的回答:
稍微长一点的回答:不要尝试这个。

说明:每个C++程序员都习惯于让比较运算符返回bool或可转换为bool的东西。只是因为键入if (a==b)之类的内容是很自然的
因此,如果表达式a==b返回布尔x,则a==b==c意味着将xc进行比较。这毫无意义。即使你让它编译,例如用这种方式比较int,它也不会产生你期望的结果。

因此,虽然技术上有,但我可以想出一个解决方案来解决你似乎想要的问题(如果三者都相等,则进行比较(,正确的做法是如何在C++中始终进行:逻辑链二进制比较:

if (a==b && b==c) {}

对于那些想知道"技术可行,但太难看了"解决方案的人:
(不要在现实世界中这样做!如果这样做,你应该被解雇。(

template <class T>
struct multiCompareProxy {
  bool b;
  T const& t;
  explicit operator bool() const {return b;}
  multiCompareProxy operator==(T const& rhs) {
    return {b && t.equals(rhs), t};
  }
};
template <class T>
multiCompareProxy<T> operator==(T const& lhs, T const& rhs) {
  return {lhs.equals(rhs), lhs};
}

一个类现在只需要重载euqals方法就可以了:示例

如果出于任何原因真的想要这样做,您需要一个代理对象,如下所示:

struct A {};
struct Proxy {};
Proxy operator==(const A& a, const A& b) {
    return {};
}
bool operator==(const Proxy& p, const A& b) {
    return true;
}
bool operator==(const A& a, const Proxy& p) {
    return true;
}

#include <iostream>
int main() {
    A a, b, c;
    if(a == b == c) {
        std::cout << "Bad.n";
    }
}

但是不要这样做。像其他人一样使用(a == b) && (a == c)

这是可以做到的,而且它作为一种领域特定语言(DSL(非常有用,可以匹配非C++程序员所期望的表示法,但对于其他用途,应该谨慎避免使用它,因为如果随意使用它,它会让编写代码的程序员感到困惑(和烦恼(。

class A
{
    // ...
    bool equals(const A& rhs) const { return ... }
    struct X
    {
        X(const A& a, bool b) : a_(a), b_(b) { }
        X& operator==(const A& rhs) const { b_ &= a_.equals(rhs); return *this; }
        explicit operator bool() const { return b_; }
        // remove explicit pre C++11 / consider making it operator void*() ...
        const A& a_;
        mutable bool b_;
    };
    X A::operator==(const A& rhs) const
    {
        return X(*this, equals(rhs));
    }
};

(如果您有隐式构造函数,您可能更喜欢独立函数(。

使用hackery的相同类型的代理允许各种意想不到的符号,如3 < x < 9x == a1 || a2 || a3。。。同样,避免它们,除非这会对代码的维护者产生巨大的影响(理想情况下,代码与系统中的其他C++代码有非常清晰的界限(。

作为这些技术的一个良好使用示例,请考虑boost spirit库,它不寻常地使用了大量运算符来提供近似BNF的符号。。。。

您不能(减去丑陋破解的可能性(重载operator==(...)以按照您指定的方式工作。

如果你想一想它会做什么,a == b会变成true或false(bool(,那么你就剩下(<bool> == c)了。做你想做的事情的正确方法是某种形式的(a==b) && (b==c)

有时你可以重载一个操作符来按照你描述的方式工作,但它必须返回它所使用的相同类型。例如:

class A
{
  A& operator+=(A const& rhs)
  {
     // operator logic
     return *this;
  }
}

这种情况之所以有效,是因为对于a += b += c,您将执行(b += c),它将返回一个A&,其余的a.operator+=(...)将其作为参数接受。

bool operator==(T const & a, T const & b) {
     return /*boolean expr*/
}

如果你有一门课,你可以做:

class MyClass {
public:
    bool operator==(T const & rhs) const {
       return /*boolean expr*/
    }
}

不要连续使用==两次,你不能,做:

a == b && b == c

我会写:

bool operator==(const A& lhs, const A& rhs){ /* do actual comparison */ }

并将其与和操作一起使用两次。