2012-04-02 12 views
1

私はPImplをかなり使い慣れています。私が自分自身で見つけたものは、正確にPimplの構造体のメンバーを初期化する場所です。オプションは、Private構造体のコンストラクタを作成して初期化したり、メインクラスのコンストラクタで初期化したりすることです。pimplクラスのデフォルト値を初期化するのに最適な場所は?

myclass.hpp:

class MyClass { 
public: 
    MyClass(); 
    ~MyClass(); 
private: 
    struct Private; unique_ptr<Private> p; 
}; 

myclass.cpp:私は本当に私が何らかの理由であった場合よりも、他の二つの違いが表示されていない現状で

#include "myclass.hpp" 
#include <string> 

struct MyClass::Private { 
    int some_var; 
    std::string a_string; 

    // Option A 
    Private() : 
     some_var {42}, 
     a_string {"foo"} 
    {} 
}; 

MyClass::MyClass() : p(new MyClass::Private) { 
    // Option B 
    p->some_var = 42; 
    p->a_string = "foo"; 
} 

へ新しいPrivateオブジェクトを作成したい場合や、オブジェクトをコピーしたい場合は、オプションAが望ましい場合があります。また、初期化リスト内の変数を初期化することもできます。しかし、私はオプションBがより読みやすく、保守性が高い傾向にあることがわかりました。ここには何かがあるのですが、私はどちらが鱗を傾けているのか見ていませんか?

+0

まあ、初期化子リストを使う方がやや効率的ですが、大きな違いはありません。もっと読みやすいものを探してください。 –

+0

実装クラスが集合体である場合、 'p(new MyClass :: Impl {'a、1、true、{1,2,3}})'のようなものを言うことができます。 –

答えて

5

是非、RAIIアプローチに従って、Privateタイプのメンバーを初期化してください。あなたが物事を地元に(そしてもっと重要なのは、論理的な場所に)保管していれば、メンテナンスはあなたに感謝します。

struct MyClass::Private { 
    int const some_var; // const members work now 
    std::string a_string; 

    // Option C 
    Private(int const some_var, std::string const& a_string) : 
     some_var {some_var}, 
     a_string {a_string} 
    {} 
}; 

MyClass::MyClass() : p(new MyClass::Private(42,"foo")) { 
} 

そうでない場合:さらに重要なことは、あなたがあなたのMyClassのctorから値を渡すために持っている場合は、オプションA.

を使用する場合は、Privateのための適切なコンストラクタを作成しない、constのメンバーを持つことができるようになりますPrivateのメンバーはデフォルトで構築され、後で上書きされます(intでは無関係ですが、より複雑なタイプについてはどうでしょうか?)。

+0

この答えは、RAIIのアプローチに従っている点があり、constメンバーは私が見ていないものがあるかどうか尋ねたときに探していたものです。乾杯。 –

1

上記の@Charles Salviaですでに述べたように、変数が割り当てられる前に変数がデフォルトで構築されているため、2つのコンストラクタのいずれかの代入でオーバーヘッドが発生します。このオーバーヘッドの量は、変数のタイプに大きく依存します。

これを受け入れることができれば、私は最も読みやすいバージョンの方が最適だと思います。だから、もしあなたがMyClassのコンストラクタでもっとも可読性の高い割り当てを見つけたら、それを求めてください。

ただし、初期化子リスト(Private c'torの場合)、つまりメンバー変数にデフォルトのコンストラクターがない場合や、参照や定数を使用する場合は考慮しないでください。

大文字と小文字を区別したい場合がありますが、イニシャライザリストを使用する「常に」は、新しく追加されたデータメンバーのために一貫性があり、今後の証拠となります。

関連する問題