代理模式

57 篇文章 0 订阅
3 篇文章 0 订阅

代理模式:

为一个对象提供一种代理,以控制对这个对象的访问。分为静态代理和动态代理。

什么时候要用?

(1)当我们想要隐藏某个类时,可以为其提供代理类
(2)当一个类需要对不同的调用者提供不同的调用权限时,可以使用代理类来实现
(3)当我们要扩展某个类的某个功能时,可以使用代理模式,在代理类中进行简单扩展
(4)spring的aop就是使用了动态代理。

优点

(1)将代理对象与真实被调用的目标对象分离,降低了系统的耦合度
(2)保护目标对象
(3)增强目标对象

缺点

(1)会造成系统设计中类的数目增加
(2)在客户端和目标对象之间增加了代理对象,会造成请求的处理速度变慢
(3)增加系统的复杂度

原理

使用一个代理将对象包装起来,然后用该代理对象取代原始对象任何对原始对象的调用都要通过代理。代理对象决定是否以及何时将方法调用转到原始对象上。

分类

静态代理

特点
静态代理的代理类和目标对象类都是在编译期确定下来的,所以不利于程序的扩展。而且,每一个代理类只能为一个接口服务,这样一来程序开发中必然产生过多的代理。

代码实现
过程大致是这样的:
(1)被代理类(actor)出现。
(2)代理类(agent)出现,并与被代理类产生关系。(通过实现同一个接口产生联系)
(3)代理类执行方法。(判断是否接受代言的方法)

package com.revision.DesignMethod.proxyPattern;

interface Work{
    void decide();
}

class Actor implements Work{
    @Override
    public void decide() {
        System.out.println("我要听从代理人的意见!请和我的代理人交流!");
    }
}

class Agent implements Work{

    Actor a = null;

    public Agent(Actor a){
        this.a = a;
    }

    @Override
    public void decide() {
        System.out.println("你好,我是代理!");
        a.decide();
    }
}

public class StaticProxyPattern {
    public static void main(String[] args) {
        //先new一个被代理对象
        Actor actor = new Actor();
        //代理类出现,并于被代理人产生关系
        Agent agent = new Agent(actor);
        //代理人替被代理人执行方法
        agent.decide();
    }
}

动态代理

特点
动态代理是在程序运行时根据需要动态创建目标类的代理对象,客户可通过代理类来调用其它对象的方法。动态代理加入了反射,肯定会比静态代理先进一点。

代码实现
执行思路和静态代理是一样的:
(1)被代理类出现。
(2)代理类出现,并与被代理类建立关联。
(3)代理类执行方法。(main函数中调用代理类的方法,代理类处调用被代理类的方法)

package com.revision.DesignMethod.proxyPattern;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

//动态代理的使用
interface Subject{
    void action();
}
//被代理类
class RealSubject implements Subject{
    @Override
    public void action() {
        System.out.println("被代理类!");
    }
}

//代理类
class MyInvocationHandler implements InvocationHandler {

    Object obj;
    //给被代理对象进行实例化,返回一个代理类的对象
    public Object blind(Object obj){
        this.obj = obj;
        return Proxy.newProxyInstance(obj.getClass().getClassLoader(),
                obj.getClass().getInterfaces(),this);
    }

    @Override
    public Object invoke(Object proxy, Method method,Object[] args)throws Throwable {
        Object returnVal = method.invoke(obj,args);
        return returnVal;
    }
}

public class DynamicProxyPattern {
    public static void main(String[] args) {
        RealSubject real = new RealSubject();
        MyInvocationHandler handler = new MyInvocationHandler();
        Object obj = handler.blind(real);
        Subject sub = (Subject)obj;
        sub.action();
    }
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值