0

このデザインを選ばない理由:

// A.hpp
class A
{
public:
    void do_something();
};

// A.cpp
#include "A.hpp"
#include <vector>

std::vector<int> impl_database_for_do_something;

static void impl_helper_for_do_something(const std::vector<int>& database){}

void A::do_something(){ impl_helper_for_do_something(impl_database_for_do_something); }

これの代わりに:

// A.hpp
#include <vector>
class A
{
public:
    void do_something();

private:
    std::vector<int> database_for_do_something_;
    void helper_for_do_something(const std::vector<int>& database){}
};

ソース ファイルで定義された変数と静的関数を使用して、実装の詳細を非表示にしてコンパイルを高速化できますか? そうでない場合、この設計 (継承以外) の何が問題になっていますか?

4

4 に答える 4

10

最初のケースでは、プログラム全体で impl_database_for_do_something のインスタンスが 1 つしかありません。A のインスタンスごとに 1 つのインスタンスが必要です。そのため、コードはまったく同等ではありません。

于 2011-05-04T15:21:14.453 に答える
6

提案どおりに状態を格納するためにグローバルベクトルを使用する場合、クラス A の異なるインスタンスがベクトルの異なる部分を使用することを何らかの方法で確認する必要があります (そうすることの明らかな困難に加えて、異なるスレッドが使用する場合にこれがどれほど難しくなるかを検討してください) Aの異なるインスタンス)。この設計は、 A がシングルトンの場合にのみ意味があります。

于 2011-05-04T15:20:46.630 に答える
2

最初の設計には、 のすべてのインスタンスに対して1 つのベクトルがあります。後者はインスタンスごとに 1 つです。インスタンス変数とクラス変数について読んでください。A

于 2011-05-04T15:30:24.913 に答える
0

これは PIMPL: Pointer to IMPLementation ではありません。

あなたはこのようにすることができます:

// A.hpp
#include <boost/shared_ptr.hpp>

class A
{
public:
  A();
  void foo();

private:
  struct Impl;
  boost::shared_ptr<Impl> _impl;
};

// A.cpp
#include <vector>
#include "A.hpp"

struct A::Impl {
  std::vector<int> _data;
};

A::A(): _impl(new std::vector<int>()) {}

void A::foo() {
  _impl->_data.push_back(3);
}

警告:このコードは適切なコピー/代入動作を扱っていません。読者の演習として残されています。

于 2011-05-04T15:34:11.960 に答える