一、简介
中介模式定义了一个单独的(中介)对象,来封装一组对象之间的交互。将这组对象之间的交互委派给与中介对象交互,来避免对象之间的直接交互。
中介模式的设计思想跟中间层很像,通过引入中介这个中间层,将一组对象之间的交互关系(或者说依赖关系)从多对多(网状关系)转换为一对多(星状关系)。原来一个对象要跟n个对象交互,现在只需要跟一个中介对象交互,从而最小化对象之间的交互关系,降低了代码的复杂度,提高了代码的可读性和可维护性。
二、适用场景
- 复杂通信对象组
- 重用对象
三、UML类图
四、案例
飞机向其他飞机广播信息。
package main
import "fmt"
type Mediator interface {
Send(message string, sender *Airplane)
}
type Airplane struct {
Name string
Mediator Mediator
}
func NewAirplane(name string, mediator Mediator) *Airplane {
return &Airplane{Name: name, Mediator: mediator}
}
func (a *Airplane) Send(message string) {
fmt.Printf("%v sends message: %v\n", a.Name, message)
a.Mediator.Send(message, a)
}
func (a *Airplane) Receive(message string) {
fmt.Printf("%v receives message: %v\n", a.Name, message)
}
type AirTrafficControl struct {
AirplaneList []*Airplane
}
func NewAirTrafficControl() *AirTrafficControl {
return &AirTrafficControl{AirplaneList: []*Airplane{}}
}
func (atc *AirTrafficControl) RegisterAirplane(airplane *Airplane) {
atc.AirplaneList = append(atc.AirplaneList, airplane)
}
func (atc *AirTrafficControl) Send(message string, airlane *Airplane) {
for _, curr := range atc.AirplaneList {
if airlane.Name != curr.Name {
curr.Receive(message)
}
}
}
func main() {
atc := NewAirTrafficControl()
airplane1 := NewAirplane("Airplane1", atc)
airplane2 := NewAirplane("Airplane2", atc)
airplane3 := NewAirplane("Airplane3", atc)
atc.RegisterAirplane(airplane1)
atc.RegisterAirplane(airplane2)
atc.RegisterAirplane(airplane3)
airplane1.Send("Hello, everyone!")
airplane2.Send("Hello, everyone!")
airplane3.Send("Hello, everyone!")
}
五、对比
观察者模式和中介模式都是为了实现参与者之间的解耦,简化交互关系。两者的不同在于应用场景上。在观察者模式的应用场景中,参与者之间的交互比较有条理,一般都是单向的,一个参与者只有一个身份,要么是观察者,要么是被观察者。而在中介模式的应用场景中,参与者之间的交互关系错综复杂,既可以是消息的发送者、也可以同时是消息的接收者。