将主题映射到他们的观察者 - 观察者模式 GoF 书

Mapping subjects to their observers - Observer pattern GoF book

在GoF设计模式这本书中,在谈到观察者模式的实现部分时,是这样写的:

Mapping subjects to their observers The simplest way for a subject to keep track of the observers it should notify is to store references to them explicitly in the subject. However, such storage may be too expensive when there are many subjects and few observers. One solution is to trade space for time by using an associative look-up (e.g., a hash table) to maintain the subject-to-observer mapping. Thus a subject with no observers does not incur storage overhead. On the other hand, this approach increases the cost of accessing the observers.

我看不出使用散列 table 如何提高存储容量。在 Java 中,对于每个主题,我们都可以有一个观察者列表 List<Observer>。如果没有观察者附加到该主题,则列表引用将为空。如果我们使用 hash table, Map<Subject, List<Observer>,我们仍然有列表,但我们也有对主题的引用,所以这种方式是更多的内存 效率低下。不知道有没有关系,gof书上实现用的语言是Smalltalk和C++。

引用的重点似乎是,如果主体负责存储自己的观察者,在大多数主体在给定时间未被观察到的情况下,每个主体都承担存储空列表的成本(想象一下数百万科目)。

另一方面,如果将对象到观察者的映射集中到单个 Map 中,则只有(少数)观察到的对象有任何内存占用。正确指出集中式映射每个观察对象的内存成本更高,因为需要存储对对象的引用,这就是为什么这样的设计才有意义,"when there are many subjects and few observers".

注意一个更现代的优化代码以避免空集合的例子: