代入演算子を書かなければならないとき
C++ の場合、特別な理由がない限り、クラスはコピー可能にする。この辺りは、java.lang.Cloneable の位置付けとは全然違うので、Java 慣れしてる人は注意が必要。
代入演算子を宣言しなかった場合、コンパイラが自動的に生成してくれる。これは、以下のようにメンバ変数ごとの代入を行う。
C& operator = (const C& another) { // 基底クラスがある場合には、最初にそれの代入演算子が実行される。 m_1 = another.m_1; m_2 = another.m_2; // 以下、メンバ変数ごとの代入。 return *this; }
このため、以下のような場合には、専用の代入演算子を定義しなければならない。
- メンバ変数にポインタを持つ場合。
- ディープコピーではなくシャロウコピーにしたいのならば、デフォルトの代入演算子で構わない。
- 基底クラスやメンバ変数の代入演算子が例外を送出する可能性がある場合。
- これらの代入演算子のうちで最初に呼び出されるものだけは、無送出保証ではなく原子性保証に緩められる。
前者は当たり前なので忘れることは少ないし、早晩動作がおかしくなるので発見しやすい。一方、後者は忘れてしまうことが多く、例外が発生しない限りは動作がおかしくなることもないので気づきにくい。