JDK动态代理

一、什么是 动态代理

动态代理模式是对方法的横向增强,它不同于继承,继承通过对父类方法的覆盖,重新对方法进行定义,而横向增强是对方法执行前和执行后的一个增加,不重新定义方法。简单来说,就是可以在不修改源码的前提下,可以对某个方法增加功能。
代理方式有两种:
1.JDK动态代理:对接口或实现接口的类进行代理
2.CGLib动态代理:对类进行代理
本文主要介绍的是JDK动态代理

二、JDK动态代理演示
jdk动态代理机制中必不可少的类和接口,一个是InvocationHandler(接口)、另一个是Proxy(类)。
必须有一个类实现InvocationHandler接口,从而实现其中的invoke()方法,在invoke()方法中对代理的方法进行增强。
创建被代理接口及实现类

public interface Animal {
    public void eat();
}

public class Person implements Animal {
    @Override
    public void eat() {
        System.out.println("人是动物,所以需要吃东西");
    }
}

创建代理类:

//创建代理类
public class MyProxy  {
    //获取代理对象,返回增强之后的方法
    public static Object getProxy(Animal animal) {
          //获取jdk的动态代理生成代理对象
        Object proxy= Proxy.newProxyInstance(MyProxy.class.getClassLoader(),
                animal.getClass().getInterfaces()
                , new InvocationHandler() {
                    @Override
                    //重写invoke方法,当调取getProxy,invoke就会执行
                    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
                        System.out.println("在吃定西之前,还需要烹饪,讲究色香味俱全");
                        //对目标对象的方法进行增强,这是切入点
                        Object result=method.invoke(animal,args);
                        System.out.println("吃完饭之后还要收拾桌子,洗碗");
                        return result;
                    }
                });
        return proxy;
    }

结果测试:

public class Main {
    public static void main(String[] args) {
    //创建被代理类对象
        Animal person=new Person();
        将被代理对象作参数传入
        Object proxyobj=MyProxy.getProxy(person);
        Animal proxy=(Animal) proxyobj;
        proxy.eat();
    }
}

运行结果:

在吃定西之前,还需要烹饪,讲究色香味俱全
人是动物,所以需要吃东西
吃完饭之后还要收拾桌子,洗碗

Process finished with exit code 0

从以上实例中,可以看到在没有修改eat方法源码的情况下,使用jdk代理,之后,再调用eat(),是我们增强之后的方法。

注意;jdk代理必须要有接口,JDK动态代理必须要有接口,对接口中的方法进行增强,而实现类中有他特有的方法,代理类无法对他进行增强,通过Proxy对象只能得到接口对象,不能得到实现类对象,所以强转的时候,只能是接口的对象。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值