C ++の両方のパラメーターにconstを使用して演算子をオーバーライドする
-
03-07-2019 - |
質問
両方のconstパラメーターを使用してオーバーライドされた演算子関数を作成しようとしていますが、その方法がわかりません。以下に簡単な例を示します。
class Number
{
Number()
{
value = 1;
};
inline Number operator + (const Number& n)
{
Number result;
result.value = value + n.value;
return result;
}
int value;
}
ここでやろうとしていることは、2つの引数を追加関数に渡すことです。これらは両方ともconstであり、クラス内で何も変更せずに結果を返します。
const Number a = Number();
const Number b = Number();
Number c = a + b;
これは可能ですか、これをどのように実行しますか?
ありがとう、
ダン
解決
inline
はクラス宣言で理解されるため、指定する必要はありません。
ほとんどの場合、次のように、 operator +
をクラス定義外で宣言された非メンバー関数にします。
Number operator+( const Number& left, const Number& right );
Number
の内部へのアクセスが必要な場合は、クラスの friend
にする必要があります。
メンバー関数として使用する必要がある場合は、関数自体をconstにする必要があります:
Number operator+( const Number& n ) const
{ // ...
Number
などのクラスの場合、通常、 operator +
は operator + =
の観点から実装されます。通常、 operator + =
は実装が簡単で、 operator +
は個別に実装するよりも効率が低下する傾向がありません。
クラス内:
Number& operator+=( const Number& n );
クラス外:
Number operator+( const Number& left, const Number& right )
{
return Number( left ) += right;
}
または偶数:
Number operator+( Number left, const Number& right )
{
return left += right;
}
他のヒント
class Number
{
Number()
{
value = 1;
};
inline Number operator + (const Number& n) const
{
Number result;
result = value + n.value;
return result;
}
int value;
}
方法:
inline Number operator + (const Number& n) const
前の回答で十分だと感じていますが、いくつかの説明が必要だと思います。
演算子は(通常)2つのフレーバーで提供されます
1つ目は非メンバー関数で、2つ目はパラメーターが「右オペランド」であるメンバー関数です。操作の、通常は現在の変更されたオブジェクトを返します。
たとえば、クラス T
の演算子§
があるとします。 非メンバー関数として記述できます:
T operator § (const T & lhs, const T & rhs)
{
T result ;
// do the lhs § rhs operation, and puts the result into "result"
return result ;
}
またはメンバー関数として:
T & T::operator § (const T & rhs)
{
// do the "this § rhs" operation, and puts the result into "this"
return *this ;
}
さらには(非常にまれに)別のメンバー関数として:
T T::operator § (const T & rhs) const
{
T result ;
// do the "this § rhs" operation, and puts the result into "result"
return result ;
}
通常、非メンバー関数を選択する必要があります。これは、それをフレンドと宣言しないためだけです。したがって、非メンバー非フレンド関数を使用すると、オブジェクトのカプセル化が強化されます。
免責事項:他にもフレーバーがありますが、 +
、 *
、 /
などの算術演算子に限定しています。ここでは-
など、および「信頼できる」オペレーターのプロトタイプ。
演算子の使用を分析します
+
の場合:
-
a = b + c
はb
もc
も変更してはならないため、各オペランドは定数である必要があります。 -
a = b + c + d + e
のように+
を累積できるため、一時的なものが必要です。
T & T::operator += (const T & rhs)
{
// do the "this § rhs" operation, and puts the result into "this"
return *this ;
}
+ =
の場合:
- 左側のオペランドA(A + = Bから)が変更されることがわかっています。
- 左側のオペランドA(A + = Bから)がそれ自体の結果であることを知っています。
次を使用する必要があります:
T & operator + (const T & lhs, const T & rhs)
{
static T result ; // result is STATIC !!!!
// do the lhs + rhs operation, and puts the result into "result"
return result ;
}
いつものように、時期尚早な最適化はすべての悪の根源です
実稼働コードでこの種のコードを見たことがありますが、実際に発生します:
<*>著者は、一時的なものを節約したいと考えていました。この種のコードでは、 a = b + c + d
を書くと、興味深い(そして間違った)結果になります。
^ _ ^
最後になりましたが、少なくとも
このページ。このページはまだ作成中ですが、その主な用途(作業中のプロトタイプのコピー/貼り付けが簡単)は非常に便利です...