收藏:
代理模式定义如下:
代理模式:给某一个对象提供一个代理或占位符,并由代理对象来控制对原对象的访问。
代理模式是一种对象结构型模式。在代理模式中引入了一个新的代理对象,代理对象在客户端对象和目标对象之间起到中介的作用,
它去掉客户不能看到的内容和服务或者增添客户需要的额外的新服务。
代理模式包含如下三个角色:
(1) Subject(抽象主题角色):
它声明了真实主题和代理主题的共同接口,这样一来在任何使用真实主题的地方都可以使用代理主题,客户端通常需要针对抽象主题角色进行编程。
(2) Proxy(代理主题角色):
它包含了对真实主题的引用,从而可以在任何时候操作真实主题对象;
在代理主题角色中提供一个与真实主题角色相同的接口,以便在任何时候都可以替代真主题;
代理主题角色还可以控制对真实主题的使用,负责在需要的时候创建和删除真实主题对象,并对真实主题对象的使用加以约束。
通常,在代理主题角色中,客户端在调用所引用的真实主题操作之前或之后还需要执行其他操作,而不仅仅是单纯调用真实主题对象中的操作。
(3) RealSubject(真实主题角色):
它定义了代理角色所代表的真实对象,在真实主题角色中实现了真实的业务操作,客户端可以通过代理主题角色间接调用真实主题角色中定义的操作。
代码示例
静态代理:
//代理类和被代理类都需要实现的接口 public interface Movie { void play(); } //被代理的类,实际的操作所在对象 public class RealMovie implements Movie{ @Override public void play() { System.out.println("you are seeing moving"); } } //代理类,用户去调用的是这个类,这个类对象里面再去调用真实操作的对象 public class Ciema implements Movie{ RealMovie movie; public Ciema(RealMovie realMovie) { super(); this.movie=realMovie; } @Override public void play() { adFunc(); movie.play(); adFunc(); } private void adFunc() { System.out.println("guanggao..."); } } public class Test { public static void main(String[] args) { RealMovie realMovie=new RealMovie(); Movie movie=new Ciema(realMovie); movie.play(); } }
动态代理
public interface SellWine { void mainJiu(); } public class MaotaiJiu implements SellWine{ @Override public void mainJiu() { System.out.println(" sell maotai"); } } public class GuitaiA implements InvocationHandler{ private Object pingpai; public GuitaiA( Object pingpai) { this.pingpai=pingpai; } // InvocationHandler 内部只是一个 invoke() 方法,正是这个方法决定了怎么样处理代理传递过来的方法调用 // proxy 代理对象 // method 代理对象调用的方法 // args 调用的方法中的参数 @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { System.out.println(" guitai is :" +this.getClass().getSimpleName()); method.invoke(pingpai, args); System.out.println("sell ending "); return null; } } public class Test { public static void main(String[] args) { MaotaiJiu maotaiJiu = new MaotaiJiu(); InvocationHandler jingxiao1 = new GuitaiA(maotaiJiu); // loader 类加载器 // interfaces 代码要用来代理的接口 // h 一个 InvocationHandler 对象 SellWine dynamicProxy = (SellWine) Proxy.newProxyInstance(MaotaiJiu.class.getClassLoader(), MaotaiJiu.class.getInterfaces(), jingxiao1); dynamicProxy.mainJiu(); } }