语言与模式-20中介者模式

35 篇文章 1 订阅
24 篇文章 0 订阅

意图

用一个中介对象来封装一系列的对象交互。中介者使各对象不需要显式地相互引用,从而使其耦合松散,而且可以独立地改变它们之间的交互。

适用性

  • 一组对象以定义良好但是复杂的方式进行通信。产生的相互依赖关系结构混乱且难以理解。
  • 一个对象引用其他很多对象并且直接与这些对象通信,导致难以复用该对象。
  • 想定制一个分布在多个类中的行为,而又不想生成太多的子类。

Java实现

//抽象同事类
public abstract class Person {
    // 维持一个抽象中介者的引用
    protected Mediator mediator;

    protected String name;

    public Person(String name, Mediator mediator){
        this.mediator = mediator;
        this.name = name;
    }

    /**
     * 设置中介者对象
     * @param mediator
     */
    public void setMediator(Mediator mediator){
        this.mediator = mediator;
    }

    /**
     * 向中介 发送消息
     */
    protected abstract void sendMessage(String msg);

    /**
     * 从中介 获取消息
     */
    protected abstract void getMessage(String msg);
}
 //具体同事类:这里的角色是 租房者
public class Renter extends Person {

    public Renter(String name, Mediator mediator) {
        super(name, mediator);
    }

    @Override
    protected void sendMessage(String msg) {
        mediator.operation(this, msg);
    }

    @Override
    protected void getMessage(String msg) {
        System.out.println("求租者[" + name + "]收到中介发来的消息: " + msg);
    }
}
 //具体同事类:这里的角色是 房东
public class Landlord extends Person {

    public Landlord(String name, Mediator mediator) {
        super(name,mediator);
    }

    @Override
    protected void sendMessage(String msg) {
        mediator.operation(this, msg);
    }

    @Override
    protected void getMessage(String msg) {
        System.out.println("房东["+ name +"]收到中介发来的消息:" + msg);
    }
}
 //抽象中介者类
public abstract class Mediator {
    // 用于添加储存 "房东"角色
    protected List<Person> landlordList = new ArrayList<Person>();

    // 用于添加储存 "求租者"角色
    protected List<Person> renterList = new ArrayList<Person>();

    /**
     * 中介者注册房东信息
     * @param landlord 房东实体
     */
    public void registerLandlord(Person landlord){
        landlordList.add(landlord);
    }

    /**
     * 中介者注册 求租者信息
     * @param landlord 房东实体
     */
    public void registerRenter(Person landlord){
        renterList.add(landlord);
    }

    /**
     * 声明抽象方法 由具体中介者子类实现 消息的中转和协调
     */
    public abstract void operation(Person person, String message);

}
 //具体中介者类:这里的角色是 房屋出租中介
public class HouseMediator extends Mediator {

    @Override
    public void operation(Person person, String message) {
        if(person instanceof Renter){
            // 将租屋的需求消息传递给 注册了的房东们
            for(Person landlord: landlordList){
                landlord.getMessage(message);
            }
        } else if(person instanceof Landlord){
            // 将房东的出租房消息传递给 注册了的 房屋求租者们
            for(Person renter : renterList){
                renter.getMessage(message);
            }
        }
    }
}
//客户端测试类
public class Client {

    public static void main(String[] args) {
        // 实例化房屋中介
        Mediator mediator = new HouseMediator();

        Person landlordA, landlordB, renter;
        landlordA = new Landlord("房东李", mediator);
        landlordB = new Landlord("房东黎", mediator);

        renter = new Renter("小吕",mediator);

        // 房东注册中介
        mediator.registerLandlord(landlordA);
        mediator.registerLandlord(landlordB);
        // 求租者注册中介
        mediator.registerRenter(renter);

        // 求租者 发送求租消息
        renter.sendMessage("在天河公园附近租套房子,价格1000元左右一个月");
        System.out.println("--------------------------");
        // 房东A 发送房屋出租消息
        landlordA.sendMessage("天河公园学院站三巷27号四楼有一房一厅出租  1200/月  光线好 近公交站");
    }
}

Clojure实现

中介者模式类似双向的观察者模式!

观察者模式是单向的,从Subject向多个Observer传递信息!

中介者模式相当与ObserverA向Subject传递信息,再通过Subject传递给ObserverB,反之亦然!

那么就可以通过实现两个add-watch来实现类似中介者模式!

(def a (atom {}))
(def b (atom {}))

(defn func-a []
   (println "func-a invoke"))

(defn func-b []
  (println "func-b invoke"))

(add-watch a :watcherA
           (fn [key atom old-state new-state]
             (func-a)))

(add-watch b :watcherB
           (fn [key atom old-state new-state]
             (func-b)))

(reset! a {:foo "bar"})
(reset! b {:foo "bar"})
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值