ユーザー定義の型変換 を使用して、
コンストラクターまたは型変換関数を使用したオブジェクト変換を指定することができます。
初期化指定子、関数引き数、関数からの戻り値、式のオペランド、式の反復制御、選択文の変換、
および明示的型変換の標準型変換の他に、ユーザー定義の型変換が暗黙的に使用されます。
ユーザー定義の型変換には次の 2 つのタイプがあります。
単一の値を暗黙的に変換する場合、コンパイラーは、ユーザー定義の型変換を 1 つだけ (型変換コンストラクターまたは型変換関数のどちらか) を使用することができます。 次の例は、このことを示しています。
class A { int x; public: operator int() { return x; }; }; class B { A y; public: operator A() { return y; }; }; int main () { B b_obj; // int i = b_obj; int j = A(b_obj); }
コンパイラーは、ステートメント int i = b_obj を許可しません。 コンパイラーは、暗黙的に b_obj を型 A のオブジェクトに変換してから (B::operator A() を使用して)、 暗黙的にそのオブジェクトを整数に変換しなければなりません (A::operator int() を使用して)。 ステートメント int j = A(b_obj) は、 暗黙的に b_obj を型 A のオブジェクトに変換してから、 暗黙的にそのオブジェクトを整数に変換します。
ユーザー定義の型変換は、明確でなければなりません。さもないとそれらは呼び出されません。 派生クラスの型変換関数は、両方の型変換関数が同じ型に変換されない限り、 基底クラスにある別の型変換関数を隠しません。 関数の多重定義解決は、最適な型変換関数を選択します。 次の例は、このことを示しています。
class A { int a_int; char* a_carp; public: operator int() { return a_int; } operator char*() { return a_carp; } }; class B : public A { float b_float; char* b_carp; public: operator float() { return b_float; } operator char*() { return b_carp; } }; int main () { B b_obj; // long a = b_obj; char* c_p = b_obj; }
コンパイラーは、ステートメント long a = b_obj を許可しません。 コンパイラーは、A::operator int() または B::operator float() のどちらかを使用して、b_obj を long に変換できます。 B::operator char*() が A::operator char*() を隠すので、 ステートメント char* c_p = b_obj は、B::operator char*() を使用して、b_obj を char* に変換します。
引き数を持つコンストラクターを呼び出し、 その引き数型を受け入れるコンストラクターが定義されていない場合、 標準型変換だけを使用して、その引き数を、 そのクラスのコンストラクターによって受け入れ可能な別の引き数型に変換します。 そのクラス用に定義されたコンストラクターに受け入れられる型に引き数を変換するために、 他のコンストラクターや型変換関数を呼び出すことはありません。 次の例は、このことを示しています。
class A { public: A() { } A(int) { } }; int main() { A a1 = 1.234; // A moocow = "text string"; }
コンパイラーは、ステートメント A a1 = 1.234 を認めます。 コンパイラーは、標準型変換を使用して、1.234 を int に変換してから、 暗黙的に変換コンストラクター A(int) を呼び出します。 コンパイラーは、ステートメント A moocow = "text string" を許可しません。 テキスト・ストリングを整数に変換するのは、標準の型変換ではありません。
関連参照