动态代理:代理类并不是在java代码中实现,而是在运行期间生成。相比静态代理,它可以很方便被代理类的方法统一处理,如添加方法调用次数,日志功能等等。分为JDK动态代理和cglib动态代理。
JDK动态代理:(1) 代理对象不需要实现接口 (2) 代理对象的生成,利用JDK的API动态的在内存中生成。(需要我们指定创建代理对象/目标对象接口类型)
JDK动态代理API:(1) java.lang.reflect.Proxy 主类,它提供了一组静态方法来为接口生成代理类及对象。 (2) java.lang.reflect.InvocationHandler 调用处理器接口,它定义了一个invoke方法,用于集中处理动态代理类对象上的方法调用。通常在该方法上实现被代理对象的访问。即用来指明产生的代理对象要做什么事情。
例如:使用 Proxy的 newProxyInstance方法,生成动态代理对象。Proxy.newProxyInstance(targetObj.getClass().getClassLoader(), targetObj.getClass().getInterfaces(), this) 其参数:1 目标对象加载器 2 目标对象接口 3 返回this
/** * @date: 2022/6/4 20:37 * @desc: 被代理对象接口 */ public interface ISay { void say(); } import java.lang.reflect.InvocationHandler; import java.lang.reflect.Method; import java.lang.reflect.Proxy; /** * @date: 2022/6/4 20:40 * @desc: 动态代理对象 */ public class ProxyInvocation implements InvocationHandler { private Object targetObj; public Object bindObj(Object p_targetObj) { targetObj = p_targetObj; // 1 目标对象加载器 2 目标对象接口 3 返回this return Proxy.newProxyInstance(targetObj.getClass().getClassLoader(), targetObj.getClass().getInterfaces(), this); } public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { return method.invoke(targetObj, args); } } /** * @date: 2022/6/4 20:38 * @desc: 被代理对象 */ public class Say implements ISay { public void say() { System.out.println("目标方法输出的内容"); } } // 测试代码 ISay say = (ISay)new ProxyInvocation().bindObj(new Say()); say.say();