Subject Observer, Publish Subscribe, Callback.
Define a one-to-many dependency between objects so that when one object changes state, all its dependents are notified and updated automatically.
The two basic styles of notification: PushModel
. If the observed object does not have the necessary hooks for observers, the observers must rely on repeatedly polling the observed to note the changes. This is a "pull" versus a "push" type of pattern. Quite appropriate for certain applications.
A key tenet is that the observed does not know anything about the observers. It "publishes" a change and the observers get notified of the change.
is useful mostly for dynamic
relationships between objects: you can hook up a new observer to an observable while the program is running (e.g. hook up a newly-opened viewing window to a domain object), then unhook it later (e.g. remove the window from the list of observers when the user closes it).
is pretty low-level, and appears in its entirety as part of other important patterns (e.g. ModelViewController
It is also the basis for publish-subscribe messaging architectures.
I have thought about this some in the Publisher/Subscriber version, as follows:
Suppose the system has an EventHandler
that wants to send out Notification X whenever this event occurs. You have a priority component, Component A, which is (probably) there all the time and may have to see this message right away. You also have a bunch of dynamic secondary components (B, C, and D) which may be there or not. They all have to receive the message sooner or later. Let's look at some possible scenarios:
- Nothing is very time critical. Publisher sends out Note X to A, B, C, D...ad nauseum. B, C, and D all begin reacting to X. In the mean time, A gets all panicky and generates event Y. Notification Y (effectively a Cancel X) goes out to B, C, et al, and these components all roll their eyes, mutter something about these kids not being able to make up their minds, and toss the work they did to process the X note. Done.
- Some things are time critical. X goes out as a conditional X. This means that a follow-up message will come out within a certain maximum time to confirm or cancel the X event. A gets a chance to chew on the X note and then generate a Confirm or Cancel. B, C, and D can all get their house in order in case this is the real thing. If they get a Confirm follow-up they complete the processing of X. Otherwise they get a Cancel and they can drop the whole thing. That finishes that.
- The worst case is where A is dynamic as well as the rest of the subscribers and time is critical. Without A in the picture Note X just goes out to whoever else is there. When A comes into the picture it has to register with the X EventHandler. Then the X handler sends a conditional X notification. The business with the Confirm or Cancel still applies.
Additionally, the Publisher can use a "Stay Current" mechanism to interrogate the Subscribers and find out if they are still there. If any subscriber disappears the Publisher drops him from the distribution list. There are many other permutations to this pattern.
Other reference sources: