模板化天文台模式

时间:2015-07-07 19:47:26

标签: c++ shared-ptr

实施观察者模式。我希望每个观察者都存储一个指向它所注册的主题的指针。因此,每个观察者都有一个指针Subject *和一个setSubject(Subject *)函数。

#include <iostream>
#include <memory>
#include <set>

template <class T>
class Subject;

template <class T>
class Observor
{
  public :
  virtual void update(const T& t) = 0;
  virtual ~Observor(){}

  void setSubject(Subject<T>* subjectPtr)
  {
    _subject = subjectPtr;
  }

   private:
   Subject<T>* _subject;
};

template<class T>
class Subject
{
  public :
  virtual void registerObservor(std::shared_ptr< Observor<T> > obv) = 0;
  virtual ~Subject(){}
};

template<class T>
class WeatherStation : public Subject<T>
{
  public :
  void registerObservor(std::shared_ptr< Observor<T> > obv)
  {
    obv->setSubject(this);
    _observors.insert(obv);
  }

  private :
  std::set< std::shared_ptr< Observor<T> > > _observors;
};

class StatisticsDisplay : public Observor<int>
{
  public :
  void update(int data){ std::cout<<"Statistics Display"; }
};

下面的主要编译没有问题。

int main()
{
  WeatherStation<int> wStation;
}

但是,当主要更改为

int main()
{
  WeatherStation<int> wStation;
  auto sDisplay = std::make_shared<StatisticsDisplay>();
}

代码现在无法编译。它告诉我错误在alloc_traits.h:第254行。由于alloc_traits.h是一个标准库,错误肯定在我的代码中。然而,我却不知道出了什么问题。

2 个答案:

答案 0 :(得分:1)

您需要使用

void update(const int& data){ std::cout<<"Statistics Display"; }

而不是

void update(int data){ std::cout<<"Statistics Display"; }
StatisticsDisplay中的

。否则,StatisticsDisplay仍然是纯虚拟类。

答案 1 :(得分:1)

如果使用clang进行编译,则会收到描述性警告和错误消息:

main.cpp:49:8: warning: 'StatisticsDisplay::update' hides overloaded virtual function [-Woverloaded-virtual]

  void update(int data) { std::cout<<"Statistics Display"; }

       ^

main.cpp:12:16: note: hidden overloaded virtual function 'Observor<int>::update' declared here: type mismatch at 1st parameter ('const int &' vs 'int')

  virtual void update(const T& t) = 0;
...

main.cpp:12:16: note: unimplemented pure virtual method 'update' in 'StatisticsDisplay'

  virtual void update(const T& t) = 0;

               ^

为了编译代码,您需要更改StatisticsDisplay::update以匹配虚函数的签名:

class StatisticsDisplay : public Observor<int>
{
  public :
  void update(const int& data){ std::cout<<"Statistics Display"; }
};