如何在重载运算符中引用当前结构?

发布于 2024-08-02 22:00:09 字数 558 浏览 5 评论 0原文

我有一个结构体,我想通过定义 << 来定义相对顺序。 ,> 、<= 和 >= 运算符。实际上,按照我的顺序,不会有任何相等,因此如果一个结构不小于另一个结构,它会自动更大。

我像这样定义了第一个运算符:

struct MyStruct{
...
...

bool operator < (const MyStruct &b) const {return (somefancycomputation);}

};

现在我想基于这个运算符定义其他运算符,这样 <= 将返回与 <= 相同的结果。另外两个只会返回相反的结果。 例如对于 >我想写一些类似的东西

bool operator > (const MyStruct &b) const {return !(self<b);}

,但我不知道如何引用这个“self”,因为我只能引用当前结构内的字段。

整个都是用 C++ 写的,

希望我的问题可以理解:)

谢谢你的帮助!

I have a struct for which i want to define a relative order by defining < , > , <= and >= operators. actually in my order there won't be any equality, so if one struct is not smaller than another, it's automatically larger.

I defined the first operator like this:

struct MyStruct{
...
...

bool operator < (const MyStruct &b) const {return (somefancycomputation);}

};

now i'd like to define the other operators based on this operator, such that <= will return the same as < and the other two will simply return the oposite.
so for example for the > operator i'd like to write something like

bool operator > (const MyStruct &b) const {return !(self<b);}

but i don't know how to refere to this 'self' since i can refere only to the fields inside the current struct.

whole is in C++

hope my question was understandable :)

thank you for the help!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

无所的.畏惧 2024-08-09 22:00:09

自我是*this

也就是说,this 是一个指向当前对象的指针,因此您需要取消引用它才能获取实际的对象。

Self is *this.

That is, this is a pointer to the current object, so you need to dereference it to get the actual object.

太阳公公是暖光 2024-08-09 22:00:09

如果您提供具有所有适当逻辑的运算符<,那么(无论它是否作为自由函数实现)您可以将其他运算符作为自由函数实现。这遵循在可能的情况下优先选择非成员而不是成员的规则,并且自由函数在左右操作数的转换方面将具有相同的行为,而作为成员函数实现的运算符则不然。

例如

inline bool operator>(const MyStruct& a, const MyStruct&b)
{
    return b < a;
}

inline bool operator<=(const MyStruct& a, const MyStruct&b)
{
    return !(b < a);
}

inline bool operator>=(const MyStruct& a, const MyStruct&b)
{
    return !(a < b);
}

If you are providing an operator< with all the appropriate logic then (whether or not it is implemented as a free function) you can implement the other operators in terms of it as free functions. This follows the rule of preferring non-members over members where possible and free functions will have identical behaviour w.r.t. conversions of the left and right operands, whereas operators implemented as member functions don't.

e.g.

inline bool operator>(const MyStruct& a, const MyStruct&b)
{
    return b < a;
}

inline bool operator<=(const MyStruct& a, const MyStruct&b)
{
    return !(b < a);
}

inline bool operator>=(const MyStruct& a, const MyStruct&b)
{
    return !(a < b);
}
左秋 2024-08-09 22:00:09

这意味着对 元素的答案

template< class Derived >
class Comparable {
  public:
    bool operator !=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) == rhs ); }

    bool operator <(const Derived& rhs) const
    {return rhs < static_cast<Derived&>(*this); } 

    bool operator >=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) < rhs ); }

    bool operator <=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) > rhs ); }
};

struct MyStruct : public Comparable<MyStruct> {
    bool operator ==(const MyStruct & rhs) const
    {return /* whatever */; }

    bool operator <(const MyStruct & rhs) const
    {return /* whatever */; }
};

This is meant as a slight improvement over Element's answer:

template< class Derived >
class Comparable {
  public:
    bool operator !=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) == rhs ); }

    bool operator <(const Derived& rhs) const
    {return rhs < static_cast<Derived&>(*this); } 

    bool operator >=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) < rhs ); }

    bool operator <=(const Derived& rhs) const
    {return !( static_cast<Derived&>(*this) > rhs ); }
};

struct MyStruct : public Comparable<MyStruct> {
    bool operator ==(const MyStruct & rhs) const
    {return /* whatever */; }

    bool operator <(const MyStruct & rhs) const
    {return /* whatever */; }
};
你的呼吸 2024-08-09 22:00:09

重载运算符只是一个成员函数,尽管语法很奇特。
您可以像这样显式调用它:


this->operator<( b );

或者为自己节省一些头发:),只需提供 intcompare( const MyStruct& ) 成员函数并在所有非成员比较运算符中使用它。

Overloaded operator is just a member function though with a fancy syntax.
You can explicitly call it like this:


this->operator<( b );

or save yourself some hair :) and just provide int compare( const MyStruct& ) member function and use that in all the non-member comparison operators.

-残月青衣踏尘吟 2024-08-09 22:00:09

这是指向当前对象的指针。所以(正如 @Dave Hinton 所说)你必须取消引用它。但是,还有另一种选择

两种选择:

return !(*this<b)

or

return (!this->operator<(b))

是的,第一个更好。

this is a pointer to your current object. So (as @Dave Hinton says) you'd have to dereference it. But, theres another option

Two options:

return !(*this<b)

or

return (!this->operator<(b))

Yes, the first one is quite nicer.

赤濁 2024-08-09 22:00:09

实际上,按照我的顺序,不会有任何相等,因此如果一个结构不小于另一个结构,它会自动更大。

这是一个问题。 C++ 操作(以及许多算法)需要严格的弱排序,其中(其他)意味着 x == x 对于任何 x 都成立。更一般地说:

not (x < y) and not (y < x)

暗示

x == y

任何xy。换句话说:您很可能必须为您的结构定义某种等式才能与任何传统算法一起使用。

actually in my order there won't be any equality, so if one struct is not smaller than another, it's automatically larger.

That's a problem. C++ operations (and many algorithms) require a strict weak ordering, which (among others) implies that x == x holds for any x. More generally:

not (x < y) and not (y < x)

implies

x == y

for any x and y. In other words: you most probably must define some kind of equality for your struct to work with any conventional algorithm.

弥繁 2024-08-09 22:00:09

我同意上面的 Tom/Dave 的直接写法:

return !(*this<b);

但对我来说,最明确清晰的形式是:

return !operator<(b);

和 Tom 的: return !(this->operator<(b));似乎有点傻。

这个有点讨厌的 C 预处理器代码(我还有一个更好但更具技术性的模板解决方案):

#define CREATE_SYMETRIC_ORDINAL_OPERATORS(Type) \
int operator !=(Type X) {return !((*this)==X); } \
int operator <(Type X) {return !((*this)>=X); } \
int operator >=(Type X) {return (((*this)>X)||((*this)==X)); } \
int operator <=(Type X) {return (((*this)<X)||((*this)==X)); }

自动定义所有比较运算符,假设 == 和 >定义如下:

class Comparable {
  public:
    int operator ==(Comparable B);
    int operator >(Comparable B);
    CREATE_SYMETRIC_OPERATORS(Comparable);
};

I'm with Tom/Dave above in that the direct way to write this:

return !(*this<b);

but for me the most explicitly clear form is:

return !operator<(b);

and Tom's: return !(this->operator<(b)); seems a little silly.

This little bit nasty C preprocessor code (I also have a better but more technical template solution):

#define CREATE_SYMETRIC_ORDINAL_OPERATORS(Type) \
int operator !=(Type X) {return !((*this)==X); } \
int operator <(Type X) {return !((*this)>=X); } \
int operator >=(Type X) {return (((*this)>X)||((*this)==X)); } \
int operator <=(Type X) {return (((*this)<X)||((*this)==X)); }

automatically defines all comparison operators assuming == and > are defined like so:

class Comparable {
  public:
    int operator ==(Comparable B);
    int operator >(Comparable B);
    CREATE_SYMETRIC_OPERATORS(Comparable);
};
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文