代理模式

《设计模式之禅》Proxy_Pattern--代理模式_代理模式

这一章以潘金莲和王婆以及西门庆三人的故事作为程序的对象,下面就通过西门庆与潘金莲的故事来理解代理模式,途中车速过高,各位请系好安全带,发车喽!!!

什么是代理模式呢?我很忙,忙的没空理你,那你要找我呢就先找我的代理人吧,那代理人总要知道被代理人能做哪些事情不能做哪些事情吧,那就是两个人具备同一个接口,代理人虽然不能干活,但是被代理的人能干活呀。

比如西门庆找潘金莲,那潘金莲不好意思答复呀,咋办,找那个王婆做代理,表现在程序上时这样的:

定义接口

这个接口我们只定义两个函数去工作,也就是把一类女人抽象出来,而这类女人能干什么事情,具体怎么干,就需要实现这个接口的类来去做

/**
 * @author LeeZhi
 * @version 1.0
 */
public interface KindWomen {
    //这中类型的女人会做什么事呢?
    public void makeEyesWithMan();//抛媚眼

    public void happyWithMan(); //happy what? you know that!

}

实现类

潘金莲类

小潘实现了这个上面所定义的接口,自然也就要实现这类女人该做什么

/**
 * @author LeeZhi
 * @version 1.0
 * 定义潘金莲是一个什么样的人
 */
public class PanJinLian implements KindWomen{

    @Override
    public void makeEyesWithMan() {
        System.out.println("小潘在抛媚眼");
    }

    @Override
    public void happyWithMan() {
        System.out.println("小潘在和男人那个");
    }
}

王婆类

这里王婆的默认构造器不写入参数,那她就是小潘的代理人,也就是被代理类,如果传入了其他的,传入谁,代理谁

这里的有参构造器后面再说,我们先看小潘的故事

/**
 * @author LeeZhi
 * @version 1.0
 * 额,王婆什么姿色不用我多说了吧,没人会喜欢
 * 但是她有经验有智慧,可以作为一类女人的代理!
 */
public class WangPo implements KindWomen{
    private KindWomen kindWomen;

    public WangPo() {//无参构造器,默认是潘金莲的代理
        this.kindWomen = new PanJinLian();
    }

    //她可以是KindWomen的任何一个女人的代理,只要你是这一类型
    public WangPo(KindWomen kindWomen) {
        this.kindWomen = kindWomen;
    }

    @Override
    public void makeEyesWithMan() {
        this.kindWomen.makeEyesWithMan();//王婆年龄大了,谁还看她抛媚眼
    }

    @Override
    public void happyWithMan() {
        this.kindWomen.happyWithMan();//自己干不动了,让年轻的来代替自己,欸嘿嘿!??
    }
}

男主角西门庆类(DeBug看实现)

水浒里是这样写的:西门庆被潘金莲用竹竿敲了一下雅道,痴迷了,

被王婆看到了,就开始撮合两人好事,王婆作为潘金莲的代理人

收了不少好处费,那我们假设一下:

如果没有王婆在中间牵线,这两个不要脸的能成吗?难说的很!

public class XiMenQing {
    public static void main(String[] args) {
        //把王婆叫出来
        WangPo wangPo = new WangPo();
        //然后西门庆就说,我要和潘金莲nappy,然后王婆就安排了西门庆丢筷子的那出戏:
        wangPo.makeEyesWithMan();
        wangPo.happyWithMan();//看到没,虽然表面上时王婆在做,实际上爽的是潘金莲
    }
}

在这里我们追溯一下debug,看一下代理类是如何让被代理类(委托类)干活

《设计模式之禅》Proxy_Pattern--代理模式_初认识_02

看的出来,现在是王婆在干活哈

《设计模式之禅》Proxy_Pattern--代理模式_代理模式_03

继续下一步时,我们可以看到了,因为王婆是潘金莲的代理人,他的无参构造器默认是潘金莲的实例化

《设计模式之禅》Proxy_Pattern--代理模式_代理模式_04

王婆这个委托类调用的潘金莲这个类对象的相关方法,给西门庆提供特定服务

那这就是活生生的一个例子,通过代理人实现了某种目的,如果真去掉王婆这个中间环节,直接是西门庆和潘金莲勾搭,估计很难成就武松杀嫂事件。

贾氏!??

那我们再考虑一下,水浒里还有没有这类型的女人?有,卢俊义的老婆贾氏(就是和那个固管家苟合的那个),那我们也让王婆做她的代理:

public class JiaShi implements KindWomen {
    @Override
    public void makeEyesWithMan() {
        System.out.println("贾氏抛媚眼");
    }

    @Override
    public void happyWithMan() {
        System.out.println("贾夫人正在happy中");
    }
}

西门庆勾引贾氏

public static void main(String[] args) {
        //把王婆叫出来
        WangPo wangPo = new WangPo();

        //西门庆勾引贾氏
        JiaShi jiaShi = new JiaShi();
        wangPo = new WangPo(jiaShi);

        wangPo.makeEyesWithMan();
        wangPo.happyWithMan();
    }
}

《设计模式之禅》Proxy_Pattern--代理模式_初认识_05

不难看出,王婆还是那个王婆,内部调用的还是贾氏的方法

总结

说完这个故事,那额总结一下,代理模式主要使用了Java的多态,干活的是被代理类,代理类主要是接活,你让我干活,好,我交给幕后的类去干,你满意就成,那怎么知道被代理类能不能干呢?同根就成,大家知根知底,你能做啥,我能做啥都清楚的很,同一个接口呗。

写在后面

代理模式在Java设计中用处颇多,Java又分为静态代理和动态代理,动态代理又有很多种,例如JDK代理和CGlib代理。像我们现在主流的框架Spring里的Aop就使用了代理模式,因为博主旨在介绍什么是代理模式,让本小白理解代理模式是什么如何实现,就不会在本系列过多的讲述代理模式的应用。(说起来也是没实力去阐述明白框架里如何使用的,请轻点喷)