class math_vector2D{
private:
int x,y;
//~省略~
public:
bool operator<(const math_vector2D&)const;
bool operator==(const math_vector2D&)const;
//~省略~
};
このとき、一般にどのような結果が与えられると期待される、またはどのような結果を与える実装をすべきなのでしょうか。
とりあえず3パターン考え、個人的には1. に追加でIsSame関数等でコピーであるかようなオブジェクトかを判定するのが良いのかと思いましたが、どうなのでしょうか。
- operator<()を一方向ハッシュ値の比較などで実装し、operator==()はoperator<に実装を委譲
→operator==()でtrueが得られてもオブジェクトの値が等しいとは限らない - operator<()を優先順位を付ける等の方法で厳密に大小関係を決定する実装にし、operator==()はoperator<に実装を委譲
→operator==()でtrueが得られれば2つのオブジェクトは等しい
→しかし大小関係の優先順位は客観的とは言えないかもしれない - operator<()を一方向ハッシュ値の比較などで実装し、operator==()はoperator<と独立に一方がもう一方のコピーであるかを判定するかのような実装にする
→operator==でtrueが得られれば2つのオブジェクトは等しい
→operator<=() は operator<() && operator==() と !(operator>() ) 両方とは等しくならないかもしれない?
具体例
1.実装例 → this->x==other.y && this->y == other.x でoperator==()はtrueになってしまう
bool math_vector2D::operator<(const math_vector2D& other)const{
return this->x * this->y < other.x * other.y ;
}
bool math_vector2D::operator==(const math_vector2D& other)const{
return ( ( *this < other)&&(other<*this) );
}
bool math_vector2D::operator<(const math_vector2D& other)const{
if( this->y == other.y ) {
return this->x < other.x;
}else{
return this->y < other.y;
}
}
bool math_vector2D::operator==(const math_vector2D& other)const{
return ( ( *this < other)&&(other<*this) );
}
bool math_vector2D::operator<(const math_vector2D& other)const{
return this->x * this->y < other.x * other.y ;
}
bool math_vector2D::operator==(const math_vector2D& other)const{
return ( ( this->x == other.x )&&( this->y == other.y ) );
}
a(1,2), b(2,1), c = a, d(3,3);
a<b //false ・・・(1)
b<a //false ・・・(2) ( = a>b )
a==b //false ・・・(3)
a==c //true
b==c //false
a<d //true
b<d //true
//このとき下の結果は・・・?
a<=b
// operator>()から実装( 例えば !( operator>() ) ) →(2)から !(false) = true
// operator<()とoperator==から実装( 例えば( operator<() && operator==() ) ) →(1)と(3)から ( false && false ) = false;