Java学习-JDK动态代理

代理模式

什么是代理模式?
代理模式就是找一个中介帮你办一些事。你只需要关注自己的事就行了,其他的中介会帮你办好。

代理模式中有三个要素:

  • 抽象对象:接口
  • 代理对象:类
  • 真实对象:类

静态代理

静态代理:有你自己来创建代理对象,每个真实对象都需要由你来创建代理对象。
缺点:如果有很多个真实对象需要被代理,那你需要写很多的代理类。

静态代理的主要思路就是:在代理类中放一个被代理类的对象,通过代理类去实现被代理类的方法。而在被代理方法执行之前或之后,你可以进行一些额外的操作。

代码实现:

interface Eat{
    void eat();
}
//真实类
class Person implements Eat{

    private String name;

    Person(String name){
        this.name = name;
    }
    public String getName(){
        return this.name;
    }

    @Override
    public void eat() {
        System.out.println(this.name+"吃饭");
    }
}
//代理类
class ProxyPerson implements Eat{

    private Person person;

    ProxyPerson(Person person){
        this.person = person;
    }

    @Override
    public void eat() {
        System.out.println("帮"+person.getName()+"做饭");
        person.eat();
        System.out.println("帮"+person.getName()+"洗碗");
    }
}
public class StaticProxyTest {
    public static void main(String[] args) {
        ProxyPerson pp = new ProxyPerson(new Person("小明"));
        pp.eat();
    }

}

运行结果:
在这里插入图片描述

这就是一个静态代理的例子。

动态代理

在静态代理中,代理类是固定的,而动态代理就是可以让代理类动态的生成。这里使用的反射机制。
动态代理通过一个Proxy类和InvocationHandler接口来动态的创建代理类。

代码实现:

interface Eat{
    void eat();
}
//真实类
class Person implements Eat{

    private String name;

    Person(String name){
        this.name = name;
    }
    public String getName(){
        return this.name;
    }

    @Override
    public void eat() {
        System.out.println(this.name+"吃饭");
    }
}
class MyInvocationHandler implements InvocationHandler{

    private Object obj;

    MyInvocationHandler(Object obj){
        this.obj = obj;
    }

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("做饭");
        method.invoke(obj);
        System.out.println("洗碗");
        return null;
    }
}
public class StaticProxyTest {
    public static void main(String[] args) {
        Eat person = new Person("tom");//真实对象
        InvocationHandler handler = new MyInvocationHandler(person);
        Eat eat = (Eat) Proxy.newProxyInstance(Person.class.getClassLoader(),Person.class.getInterfaces(),handler);
        eat.eat();
    }

}

运行结果:
在这里插入图片描述

动态代理实现步骤

Proxy.newProxyInstance(Person.class.getClassLoader(),Person.class.getInterfaces(),handler);

这句话主要是用来创建一个代理类的对象。
在newProxyInstance这个方法中,先使用反射创建了一个代理类,代理类实现了Person所实现的接口。在代理类中还有一个带有InvocationHandler为参数的构造器,在调用代理对象的方法时,实际上调用的是InvocationHandler中的invoke方法。

总结

今天只是大概的了解一下静态代理和动态代理,对他们的底层实现还需要慢慢了解。

posted @ 2020-05-19 16:14  Z-Dey  阅读(182)  评论(0编辑  收藏  举报