代理模式

代理模式

静态代理

/*
* 代理模式
* */
public class Demo {
    public static void main(String[] args) {
        // 实例化被代理类
        Demo01Impl demo01 = new Demo01Impl();
        // 使用被代理类实例化代理类
        ProxyServer proxyServer = new ProxyServer(demo01);
        /*
        * 此时有参构造后,代理类中的 private Demo01 demo01 = new DemoImpl();
        * */
        proxyServer.method01();
        /*
        * 此时进入代理类的method01()中
        * checkMethod01();
        * demo01.method01();
        * 先执行checkMethod01(),然后调用这个private Demo01 demo01 = new DemoImpl();的method01()
        *
        * 此时结果为:
        * method01的检查工作
        * 被代理类method01
        * */
    }
}

// 接口
interface Demo01 {
    void method01();
}

// 被代理类
class Demo01Impl implements Demo01 {

    @Override
    public void method01() {
        System.out.println("被代理类method01");
    }
}

// 代理类
class ProxyServer implements Demo01 {

    private Demo01 demo01;

    // 在构造器中对demo01初始化
    public ProxyServer(Demo01 demo01) {
        this.demo01 = demo01;
    }

    public void checkMethod01() {
        System.out.println("method01的检查工作");
    }

    @Override
    public void method01() {
        checkMethod01();
        demo01.method01();
    }
}

动态代理

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

/*
 * 使用反射,动态代理
 * */
public class ReDemo {
    public static void main(String[] args) {
        // 参数是一个被代理类对象
        // proxyInstance就是代理类对象
        Demo proxyInstance01 = (Demo) ProxyFactory.getProxyInstance(new DemoImpl01());
        Demo proxyInstance02 = (Demo) ProxyFactory.getProxyInstance(new DemoImpl02());
        proxyInstance01.method();
        proxyInstance02.method();
    }
}

// 接口
interface Demo {
    void method();
}

// 被代理类
class DemoImpl01 implements Demo{

    @Override
    public void method() {
        System.out.println("DemoImpl01 => method()");
    }
}

// 被代理类
class DemoImpl02 implements Demo{

    @Override
    public void method() {
        System.out.println("DemoImpl02 => method()");
    }
}

/*
* 问题:
*   1.如何根据加载到内存中的被代理类对象,动态创建一个代理类及其对象?
*   2.通过代理类的对象调用方法时如何让被代理类调用同名的方法
* */

class ProxyFactory {
    public static Object getProxyInstance(Object o) { // o是被代理类对象
        MyInvocationHandler handler = new MyInvocationHandler();
        handler.bind(o);
        return Proxy.newProxyInstance(o.getClass().getClassLoader(), o.getClass().getInterfaces(),handler);
    }
}

class MyInvocationHandler implements InvocationHandler {
    // 声明是Object,但是赋值时需要被代理类的对象进行赋值
    private Object object;

    public void bind(Object o) {
        this.object = o;
    }

    // 当我们通过代理类的对象,调用方法是,就是自动调用如下的方法:invoke()
    // 将被代理类要执行的方法的功能就声明在invoke()中
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {

        // 方法之前
        System.out.println("方法之前");
        System.out.println(method + " ===> 参数:" + Arrays.toString(args));

        // 原方法
        // method就是代理类对象调用的方法,此方法也就作为了被代理类调用的方法
        Object returnValue = method.invoke(object, args);
        return returnValue;

        // 方法之后
        System.out.println("方法之后");
    }
}
posted @ 2022-03-09 12:15  CoderCatIce  阅读(27)  评论(0编辑  收藏  举报