Java动态代理

动态代理

代理:辅助对象处理一些操作,为对象的行为做代理(明星的经纪人)。

动态代理调用方法的流程

动态代理的流程

  1. 走向代理
  2. 代理为方法额外做一些辅助工作
  3. 触发真正的对象方法执行
  4. 回到代理中,由代理返回结果给方法调用者

实现动态代理的步骤

  1. 必须定义接口
  2. 被代理对象必须实现接口
  3. 使用Proxy类提供的newProxyInstance方法,得到对象的代理对象

动态代理例子

//被代理对象的技能接口
public interface Skill {
    void sing();
    void dance();
}

//明星类(实现Skill接口)
public class Star implements Skill{
    String name;
    public Star(String name) {
        this.name = name;
    }
    @Override
    public void sing() {
        System.out.println(name + "开始唱《爱你》");
    }
    @Override
    public void dance() {
        System.out.println(name + "开始跳宅舞");
    }
}

//明星的代理人类
public class StarAgent {
    public static Skill getProxy(Star obj) {
        //3.用传入的被代理对象构造代理对象,并以接口类型返回
        return (Skill) Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), new InvocationHandler() {
            @Override
            //method:传入的方法  args:传入的参数
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                //4.额外的操作(动态代理的目的)
                System.out.println("收首付款");
                //5.真正调用被代理对象的方法
                Object result = method.invoke(obj,args);
                System.out.println("收尾付款");
                return result;
            }
        });
    }
}

//测试类
public class Test {
    public static void main(String[] args) {
        //1.实例化被代理的对象
        Star s1 = new Star("杨超越");
        //2.将被代理对象传入代理类方法
        Skill s2 = StarAgent.getProxy(s1);
        //6.实际是通过代理对象调用的方法
        s2.sing();
        s2.dance();
    }
}


输出结果:
收首付款
杨超越开始唱《爱你》
收尾付款
收首付款
杨超越开始跳宅舞
收尾付款

动态代理的作用

  1. 在不改变方法源码的情况下,增强方法功能,提高复用性

  2. 提高开发效率和可扩展性

  3. 可为被代理对象所有方法做代理

  4. 可以为任意接口的实现类对象做代理

    public class StarAgent {
        //将接口类型改为T(任意类型)
        public static <T> T getProxy(T obj) {
            return (T) Proxy.newProxyInstance(obj.getClass().getClassLoader(), obj.getClass().getInterfaces(), new InvocationHandler() {
                @Override
                //method:传入的方法  args:传入的参数
                public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                    System.out.println("收首付款");
                    Object result = method.invoke(obj,args);
                    System.out.println("收尾付款");
                    return result;
                }
            });
        }
    }
    
posted @ 2022-08-05 23:05  科班小白  阅读(59)  评论(0编辑  收藏  举报