我知道这听起来很重,但我正试图解决一个假设的情况。想象一下,你有某个对象的 N 观察者。每个人都对对象状态感兴趣。应用Observer Pattern时, observable 对象倾向于遍历其观察者列表,调用观察者notify()|update()
方法。
现在想象一下,一个特定的观察者与 observable 对象的状态有很多关系。例如,这会减慢上一次通知的速度。
因此,为了避免减慢对所有观察者的通知,我们可以做的一件事是在一个单独的线程中通知观察者。为了实现这一点,我想每个观察者都需要一个线程。这是一个痛苦的开销,我们正在努力避免因繁重工作导致的通知减慢。如果使用线程方法,最慢的是减速,是由无限循环引起的死线程。读这本经验丰富的程序员会很棒。
这是一个模糊的例子,以展示并希望澄清我甚至没有测试过的基本概念:
class Observable(object):
def __init__(self):
self.queues = {}
def addObserver(self, observer):
if not observer in self.queues:
self.queues[observer] = Queue()
ot = ObserverThread(observer, self.queues[observer])
ot.start()
def removeObserver(self, observer):
if observer in self.queues:
self.queues[observer].put('die')
del self.queues[observer]
def notifyObservers(self, state):
for queue in self.queues.values():
queue.put(state)
class ObserverThread(Thread):
def __init__(self, observer, queue):
self.observer = observer
self.queue = queue
def run(self):
running = True
while running:
state = self.queue.get()
if state == 'die':
running = False
else:
self.observer.stateChanged(state)
答案 0 :(得分:7)
你走在正确的轨道上。
每个观察者通常拥有自己的输入队列和自己的消息处理线程(或更好:队列将拥有该线程,观察者将拥有该队列)。请参阅Active object pattern。
但是有一些陷阱:
答案 1 :(得分:2)
让每个观察者自己决定它的反应是否是重量级的,如果是,则启动一个线程,或者将任务提交给一个线程池。在单独的线程中进行通知并不是一个好的解决方案:在释放可观察对象时,它会限制单线程通知的处理器能力。如果您不信任您的观察者,则创建一个线程池,并为每个通知创建一个任务并将其提交给池。
答案 2 :(得分:0)
在我看来,如果Observable有一个大没有的Observers,它会进行繁重的处理,那么最好的办法是在Observer中使用notify()
方法。 / p>
使用notify()
:只需将dirty
中的Observer
标记设置为true
即可。因此,只要Observer线程找到合适的,它就会查询 Observable以获取所需的更新。
这不需要在Observable
方面进行大量处理,将负载转移到Observer
方。
现在,当他们必须观察时,它取决于Observers
。
答案 3 :(得分:0)
@Pathai的答案在很多情况下都是有效的。
一个是您正在观察数据库中的更改。在许多方面,您不能仅从快照中重构最终状态,特别是如果您的状态是作为复杂查询从数据库中获取的,并且快照是对数据库的更新。
要实现它,我建议使用一个Event对象:
class Observer:
def __init__(self):
self.event = threading.Event()
# in observer:
while self.event.wait():
# do something
self.event.clear()
# in observable:
observer.event.set()