一文撸明白 静态代理和动态代理

先直接上代码干货

创建一个Speak接口和ZhangSan实体类

Speaker接口:
public interface Speaker {
    void speak();
}

ZhangSan类:
public class ZhangSan implements Speaker {
    @Override
    public void speak() {
        System.out.println("张三: 哈哈哈哈哈");
    }
}

这个时候,如果我们需要ZhangSan在speak之前或者之后干点啥,,,就需要使用代理类来增强目标类实现

1.采用静态代理类实现

ZhangSan代理类(增强类):
public class ZhangSanProxyer implements Speaker {
    //注入ZhangSan对象
    private ZhangSan zs = new ZhangSan();

    @Override
    public void speak() {
        System.out.println("嘻嘻嘻嘻");
        zs.speak();
        System.out.println("呵呵呵呵");
    }
}

此时,通过如下代码调用,即可实现增强

//静态代理
Speaker speaker = new ZhangSanProxyer();
speaker.speak();

 2.采用 jdk动态代理实现

创建一个代理抽象层:
public class Proxyer implements InvocationHandler {

    private Object obj;

    public Proxyer(Object obj) {
        this.obj = obj;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        if ("speak".equals(method.getName())){
            System.out.println("嘻嘻嘻嘻");
            method.invoke(obj,args);
            System.out.println("呵呵呵呵");
        }

        return null;
    }
}

此时,通过如下代码调用,即可实现增强

//jdk动态代理
Proxyer proxyer = new Proxyer(new ZhangSan());
Speaker speaker1 = (Speaker) Proxy.newProxyInstance(Demo.class.getClassLoader(),new Class[]{Speaker.class},proxyer);
speaker1.speak();

3.采用 cglib动态代理实现

创建Lisi实体类(不实现接口):
public class Lisi {
    public void speak() {
        System.out.println("李四: 哈哈哈哈哈");
    }
}

创建代理增强类实现增强:
public class Interceptor implements MethodInterceptor {

    private Object obj;

    public Interceptor(Object obj) {
        this.obj = obj;
    }

    @Override
    public Object intercept(Object o, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
        if ("speak".equals(method.getName())){
            System.out.println("嘻嘻嘻嘻");
            method.invoke(obj,args);
            System.out.println("呵呵呵呵");
        }

        return null;
    }
}

此时,通过如下代码调用,即可实现增强

//cglib动态代理
Interceptor interceptor = new Interceptor(new Lisi());
Lisi lisi = (Lisi) Enhancer.create(Lisi.class, interceptor);
lisi.speak();

总结:

代理模式:

代理模式可以在不修改被代理对象的基础上,通过扩展代理类,进行一些功能的附加与增强。值得注意的是,代理类和被代理类应该共同实现一个接口,或者是共同继承某个类。

静态代理和动态代理,都是基于代理模式实现的一种对于类的方法的增强。

 静态代理:

所谓静态代理,其实就是在编译期完成代理(程序运行前就已经存在代理类的字节码文件)

动态代理:

动态代理是利用反射机制在运行时创建代理类, 其实是对代理类做了进一步抽象和封装,提高其复用性

jdk动态代理:

两个核心对象:
invocationHandler接口, Proxy类

1.被代理类需要实现某个接口(自己定义的接口也可以)。
2.实现invocationHandler接口的类作为代理类的参数,invocationHandler接口有一个invoke抽象方法需要实现
3.使用jdk中的Proxy类的静态方法newProxyInstance()方法,生成一个代理类

cglib动态代理:

两个核心对象:
MethodInterceptor接口 ,Enhancer类

1.被代理类没有实现接口
2.创建自己的方法拦截处理器Interceptor 实现 MethodInterceptor 接口, 接口中有一个intercept方法需要实现
3.使用Enhancer.create方法创建代理增强类

 

posted @ 2021-07-24 21:27  Sherlock先生  阅读(243)  评论(0编辑  收藏  举报