java代理模式2_动态代理_jdk

2021-10-28  本文已影响0人  指下光年

动态代理

相对于静态代理,动态代理在创建代理对象上更加的灵活,动态代理类的字节码在程序运行时,由java反射机制动态产生。它会根据需要,通过反射机制在程序运行期,动态的为目标对象创建代理对象,无需手动编写源代码。动态代理简化了编程工作,提高了软件系统的可扩展性,因为反射机制可以生成任意类型的动态代理。代理的行为可以代理多个方法,即满足生产需要的同时又达到代码通用的目的。

动态代理的两种实现方式:
1. JDK 动态代理
2. CGLIB动态代理

  1. 目标对象不固定
  2. 在应用程序执行时动态创建目标对象
  3. 代理对象会增强目标对象的行为
JDK 动态代理

注:JDK 动态代理的目标对象必须有接口实现

public interface RentHouse {
    public String toRentHouse(String name);
}
public class ZuKe implements RentHouse{
    @Override
    public String toRentHouse(String name) {
        System.out.println("我要租房,预算5000");
        return "签名:"+name;
    }
}
public class JdkProxy {

    //目标对象
    private Object object;
    //构造注入
    public JdkProxy(Object object) {
        this.object = object;
    }

    /**
     * 通过调用proxy代理类中的newProxyInstance(),得到代理对象
     * @return
     */
    public Object getProxy(){
        //定义ClassLoader类加载器
        ClassLoader loader = this.getClass().getClassLoader();
        //要代理的对象提供的接口数组
        Class<?>[] interfaces = object.getClass().getInterfaces();
        //一个InvocationHandler接口,表示代理实例的调用处理程序实现的接口。
        InvocationHandler invocationHandler = new InvocationHandler() {
            /**
             * 当代理对象调用方法时,invoke方法就会被执行一次(InvocationHandler接口中的invoke方法)
             * @param proxy 代理对象
             * @param method 目标方法
             * @param args 目标方法所需要的参数
             * @return
             * @throws Throwable
             */
            @Override
            public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                System.out.println("方法执行前。。。。");
                //调用目标对象中的方法  通过反射中的invoke方法,调用指定对象的指定方法
                /**
                 * 反射invoke方法
                 *  方法名.invoke(对象,方法所需参数);
                 */
                Object s = method.invoke(object,args);
                System.out.println("方法执行后。。。。");
                //return的是方法的返回值(目标对象里面的方法)
                return s;
            }
        };
        //调用方法,得到代理对象
        Object instance = Proxy.newProxyInstance(loader, interfaces, invocationHandler);
        return instance;
    }
public class App {
    public static void main( String[] args ) {
        //目标对象
        RentHouse rentHouse = new ZuKe();
        //得到代理对象
        JdkProxy proxy = new JdkProxy(rentHouse);
        //通过代理对象得到方法
        RentHouse rentHouseProxy = (RentHouse)proxy.getProxy();
        String name = "小明";
        String s = rentHouseProxy.toRentHouse(name);
        System.out.println(s);
    }
}
上一篇 下一篇

猜你喜欢

热点阅读