コピーコンストラクタが呼び出されないことの解決方法

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
dom

コピーコンストラクタが呼び出されないことの解決方法

#1

投稿記事 by dom » 13年前

以下のコードについてです。クラスPiyoのコンストラクタ内でのポインタの初期化時に
Hogeのコピーコンストラクタが呼ばれてほしいのですが、テンプレート版の方が呼ばれてしまいます。
何かスマートな解決法はないでしょうか?

コード:

class Hoge
{
public:
	template <class T>
	explicit Hoge(T& val) { cout << "template" << endl; }

	Hoge(const Hoge& other) { cout << "copy ctor" << endl; }
};

class Piyo
{
public:
	template <class T>
	Piyo(T& val)
		: ptr(new T(val)) // コピーコンストラクタ呼び出しのつもりが、呼ばれない
	{}
private:
	shared_ptr<void> ptr;
};

int main()
{
	int forTemplate = 123;
	Hoge hoge( forTemplate ); // テンプレート版コンストラクタをよぶ
	Piyo piyo( hoge );  // hogeを内部でコピーして保持したい

	return 0;
}

YuO
記事: 947
登録日時: 15年前
住所: 東京都世田谷区

Re: コピーコンストラクタが呼び出されないことの解決方法

#2

投稿記事 by YuO » 13年前

Piyoのコンストラクタのシグネチャを,

コード:

Piyo (const T& val)
とするか,
初期化子を,

コード:

: ptr(new T(const_cast<const T &>(val))
とすればよいでしょう。

コード:

template Hoge<Hoge>(Hoge &)

コード:

Hoge (const Hoge &)
の間で,

コード:

new Hoge( /* val : Hoge & */ val)
のオーバーロードでは,前者は変換が0回に対して後者はHoge &からconst Hoge &への変換が1回あるため,前者が選ばれます。
後者に対して変換が0回になるようにしてやることで,後者を選ぶようになります。

dom

Re: コピーコンストラクタが呼び出されないことの解決方法

#3

投稿記事 by dom » 13年前

返信ありがとうございます。変換回数で決まるとは知りませんでした。
おかげで知識が増えました。ありがとうございます。

閉鎖

“C言語何でも質問掲示板” へ戻る