Java基础之动态代理

动态代理是反射机制的应用

一:概念

  

 

 动态代理举例:

 1 interface Human{
 2     String getBelief();
 3     void eat(String food);
 4 }
 5 
 6 
 7 //被代理类
 8 class SuperMan implements Human{
 9 
10     @Override
11     public String getBelief() {
12         return "I can fly...";
13     }
14 
15     @Override
16     public void eat(String food) {
17         // TODO Auto-generated method stub
18         System.out.print("我喜欢:" + food);    
19     }
20     
21 }
22 
23 //代理类
24 class ProxyFactory{
25     
26     //调用此方法,返回一个代理类的对象
27     public static Object getProxyInstance(Object obj) { //obj是被代理类的对象
28         
29         MyInvocationHandler hander = new MyInvocationHandler();
30         
31         hander.bind(obj);
32         //创建一个代理类对象的实例,传入被代理类的加载器,接口,和要处理
33         return Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), hander);
34     }
35     
36 }
37 
38//代理类的调用处理类
39 class MyInvocationHandler implements InvocationHandler{
40 
41     private Object obj;//需要使用被代理类的对象进行赋值
42     
43     public void bind(Object obj) {
44         this.obj = obj;
45     }
46     
47     //当我们通过代理类的对象调用方法a时,就会自动调用如下的invoke方法
48     @Override
49     public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
50         
51         //method即为代理类对象调用的方法,此方法也就作为了被代理类对象要调用的方法。
52         Object returnvalue = method.invoke(obj,args);
53         return returnvalue;
54     }
55     
56     
57 }
58 
59 
60 public class ProxyTest {
61     public static void main(String[] args) {
62         SuperMan superman = new SuperMan();
63         Human proxyInstance = (Human)ProxyFactory.getProxyInstance(superman);
64         proxyInstance.eat("food");
65     }
66     
67 }

注意动态代理的两个核心:

java动态代理机制中有两个重要的类和接口InvocationHandler(接口)和Proxy(类),这一个类Proxy和接口InvocationHandler是我们实现动态代理的核心;
1.InvocationHandler接口是proxy代理实例的调用处理程序实现的一个接口,每一个proxy代理实例都有一个关联的调用处理程序;在代理实例调用方法时,方法调用被编码分派到调用处理程序的invoke方法。

换句话说,每一个动态代理类都会有一个调用处理类,该类都必须实现InvocationHandler接口,并且每个代理类的实例都关联到了该类中,当我们通过动态代理对象调用一个方法时候,这个方法的调用就会被转发到该调用处理类中的invoke方法来调用。

2.Proxy类就是用来创建一个代理对象的类,它提供了很多方法,但是我们最常用的是newProxyInstance方法。这个方法的作用就是创建一个代理类对象,它接收三个参数,我们来看下几个参数的含义:
    loader:一个classloader对象,定义了由哪个classloader对象对生成的代理类进行加载. [obj.getClass().getClassLoader()]
    interfaces:一个interface对象数组,表示我们将要给我们的代理对象提供一组什么样的接口,如果我们提供了这样一个接口对象数组,那么也就是声明了代理类实现了这些接口,代理类就可以调用接口中声明的所有方法。[obj.getClass().getInterfaces()]
    h:一个InvocationHandler对象,表示的是当动态代理对象调用方法的时候会关联到哪一个InvocationHandler对象上,并最终由其调用。

 

参考:

https://www.bilibili.com/video/BV1Kb411W75N?

https://blog.csdn.net/yaomingyang/article/details/80981004

posted @ 2021-03-24 18:56  Only、  阅读(58)  评论(0)    收藏  举报