我正在尝试创建一个观察者模式,其中主题使用不同的通知通知观察者。
通常在观察者模式实现中,您只能看到一个名为“notify”的方法,它通知观察者发生了某些事情,并且具有一种反转,其中观察者持有主题的指针,并在被通知时请求主题的内容。
我正在以稍微不同的方式实现此功能,其中主题附加观察者并通知所有观察者,而无需在观察者内部持有主题的指针。例如:
通常在观察者模式实现中,您只能看到一个名为“notify”的方法,它通知观察者发生了某些事情,并且具有一种反转,其中观察者持有主题的指针,并在被通知时请求主题的内容。
我正在以稍微不同的方式实现此功能,其中主题附加观察者并通知所有观察者,而无需在观察者内部持有主题的指针。例如:
#include <iostream>
#include <vector>
class ObserverEvents
{
public:
virtual addSomethingOne(int) = 0;
virtual addSomethingTwo(float) = 0;
};
class Observer : public ObserverEvents
{
public:
Observer();
~Observer();
virtual addSomethingOne(int) {}
virtual addSomethingTwo(float) {}
};
class Subject : public ObserverEvents
{
public:
Subject() {}
~Subject()
{
for (int i = 0; i < observers.size(); ++i)
{
delete observers[i];
}
}
void attach(Observer * observer)
{
observers.push_back(observer);
}
virtual addSomethingOne(int something)
{
for (int i = 0; i < observers.size(); ++i)
{
observers[i].addSomethingOne(something);
}
}
virtual addSomethingTwo(float something)
{
for (int i = 0; i < observers.size(); ++i)
{
observers[i].addSomethingTwo(something);
}
}
private:
std::vector<Observer *> observers;
};
class FooObserver : public Observer
{
public:
BarObserver() {}
~BarObserver() {}
addSomethingOne(int something)
{
// do something with something
}
addSomethingTwo(float something)
{
// do something with something
}
};
class BarObserver : public Observer
{
public:
BizObserver() {}
~BizObserver() {}
addSomethingOne(int something)
{
// do something with something
}
addSomethingTwo(float something)
{
// do something with something
}
};
int main(int argc, char const * argv[])
{
Subject subject;
subject.attach(new FooObserver());
subject.attach(new BarObserver());
return 0;
}
我唯一关心的是是否违反了设计原则,例如开放封闭原则或类似原则,而且如果我需要添加新通知,则需要在所有其他类中实现此通知(这很痛苦-想象一下10个或更多观察者)。
我考虑过不同的方法,只创建一个接口,然后继承它创建其他通知,但有一个问题是观察者如何确定每种不同类型的通知是什么?
示例:
#include <iostream>
#include <vector>
class Notifier
{
public:
Notifier() {}
~Notifier() {}
virtual int getInt() const = 0;
};
class FooNotifier
{
public:
FooNotifier() {}
~FooNotifier() {}
int getInt() const
{
return 10;
}
};
class BarNotifier
{
public:
BarNotifier() {}
~BarNotifier() {}
int getInt() const
{
return 50;
}
};
class Observer : public ObserverEvents
{
public:
Observer();
~Observer();
virtual receive(Notifier *) = 0;
};
class Subject : public ObserverEvents
{
public:
Subject() {}
~Subject()
{
for (int i = 0; i < observers.size(); ++i)
{
delete observers[i];
}
}
void attach(Observer * observer)
{
observers.push_back(observer);
}
virtual notify(Notifier * notification)
{
for (int i = 0; i < observers.size(); ++i)
{
observers[i].receive(notification);
}
}
private:
std::vector<Observer *> observers;
};
class FooObserver : public Observer
{
public:
BarObserver() {}
~BarObserver() {}
receive(Notifier * notification)
{
// ...
}
};
class BarObserver : public Observer
{
public:
BizObserver() {}
~BizObserver() {}
receive(Notifier * notification)
{
// ...
}
};
int main(int argc, char const * argv[])
{
Subject subject;
subject.attach(new FooObserver());
subject.attach(new BarObserver());
subject.notify(new FooNotifier());
subject.notify(new BarNotifier());
return 0;
}
这个实现只是一个例子,我知道我可以使用智能指针、删除原始指针并做得更好,但它只是一种实现示例。
这种新方法的问题在于,我需要知道Notifier
的API才能在Observer内部使用它,调用getInt
。
我该怎么做,什么是最好的方式?如何向观察者发送不同的通知?