0

オーバーロードされたコンストラクターが2つあります。

Hello::Hello(std::string message)
{
}

Hello::Hello(int *number)
{
}

これらのコンストラクターのいずれかがメモリアドレスを取得できます。もし私がそうしたらHello hi(NULL);、どちらが呼ばれるでしょうか?

また、オーバーロードされたオブジェクトに関するルールを説明できれば。同様に、パラメーター()に長い時間がかかるコンストラクターと、長い( )にオーバーロードがあったオブジェクトをObject::Object(long x)受け取る別のオーバーロード( )がある場合と同様です。それから私は電話しますそれはどちらか一方を呼び出すことが保証されていますか?Object::Object(SomeOtherObject o)SomeOtherObject::SomeOtherObject(long x)Object obj((long)5);

4

3 に答える 3

2

コンストラクターを調整するstd::stringには、追加の暗黙的な変換が必要になるため、int*推奨されます。

2番目のシナリオでは、最初のコンストラクターが優先されます。コンパイラが完全に一致する他のコンストラクタを探すのはなぜですか?longまた、暗黙の変換が含まれています。これは、直接コンストラクターが提供する完全一致よりも劣ります。

于 2012-08-12T22:11:01.847 に答える
2

コンストラクターがあるということは、あなたの例とはまったく関係ありません。それは単に過負荷の解決についてであり、2つの機能でそれをチェックすることができます:

void foo(std::string s) {
}

void foo(int* n) {
}

呼び出すfoo(NULL)と、が呼び出されfoo(int*)ます。NULLはnullポインター定数であり、すべてのポインター型に暗黙的に変換できます。このコンテキストでの最適な変換は、int*です。他の過負荷は2回の変換を必要としますが、これはより悪い評価です。

2番目のシナリオは非常に明白です。完全一致が優先されます。

于 2012-08-12T22:15:23.037 に答える
1

2番目の質問で指摘した問題については、過負荷の解決を強制的に期待どおりに動作させることができます。

のように単一のオブジェクトを持つクラスコンストラクターがある場合Object(SomeOtherObject o)、スタイルごとにそのコンストラクターを単語explicitでマークする方がよいため、コンパイラーは暗黙的な変換を試みません。たとえば、定義が与えられた場合:

class A {
  A(int x);
};

class B {
  explicit B(A a);
};

のようなオブジェクトを作成しようとするB b(100)と、コンパイルエラーになります。

このトピックに関するGoogleC++スタイルガイドのセクションも参照してください。

于 2012-08-12T22:32:11.910 に答える