AOP动态代理的两种方式
大家好,今天咱们来聊聊面试高频题——AOP动态代理的两种方式。作为Java开发者,理解动态代理是掌握Spring框架核心原理的关键。在面试中,面试官特别喜欢深挖这块知识,因为它直接关系到AOP(面向切面编程)的实现机制。下面我就用最直白的语言,结合真实面试场景,给大家拆解清楚。
🔥 2025年Java面试宝典最新版
链接: https://pan.baidu.com/s/1RUVf75gmDVsg8MQp4yRChg?pwd=9b3g
提取码:9b3g
(含AOP高频考点+动态代理源码解析)
一、动态代理为什么是AOP的基石?
AOP动态代理 的本质是在运行时动态生成代理对象,在不修改源码的前提下增强方法逻辑。比如事务管理、日志打印这些横切关注点,都是靠动态代理织入的。Spring默认根据目标类选择代理方式:

二、JDK动态代理:接口的"影子替身"
JDK动态代理 是Java原生支持的代理方式,核心依赖java.lang.reflect.Proxy类。它的特点是:
- 强制要求目标类实现接口
比如你有个UserService接口和它的实现类UserServiceImpl,代理对象会实现相同接口 - 通过InvocationHandler织入逻辑
代理逻辑写在invoke()方法里,通过反射调用原方法 - 性能中等但兼容性好
由于基于反射,比直接调用略慢,但无需引入额外库
// 伪代码示例:面试口述时可这样描述
Object proxy = Proxy.newProxyInstance(
target.getClassLoader(),
target.getClass().getInterfaces(),
(proxy, method, args) -> {
System.out.println("【前置增强】");
Object result = method.invoke(target, args);
System.out.println("【后置增强】");
return result;
}
);
三、CGLIB动态代理:类的"基因改造"
当目标类没有实现接口时(比如古老的三层架构Dao类),Spring就会启用CGLIB动态代理:
- 通过字节码技术生成子类
代理类继承目标类,因此不能代理final方法 - MethodInterceptor拦截方法
增强逻辑写在intercept()方法中 - 性能优于JDK代理
早期版本生成慢但执行快,新版本ASM优化明显
// 伪代码示例:口述重点
Enhancer enhancer = new Enhancer();
enhancer.setSuperclass(TargetClass.class);
enhancer.setCallback((MethodInterceptor) (obj, method, args, proxy) -> {
System.out.println("【CGLIB前置增强】");
Object result = proxy.invokeSuper(obj, args);
System.out.println("【CGLIB后置增强】");
return result;
});
TargetClass proxy = (TargetClass) enhancer.create();

四、两种动态代理的面试对比指南
| 特性 | JDK动态代理 | CGLIB动态代理 | |--------------|-----------------------------|----------------------------| | 代理对象 | 实现目标接口 | 继承目标类 | | 限制 | 必须实现接口 | 不能代理final方法/类 | | 性能 | 调用反射略慢 | 生成慢但执行快 | | 依赖 | JVM内置支持 | 需引入cglib库 |
💡 面试话术:
“Spring Boot 2.x开始默认使用CGLIB,因为现在很多项目用注解开发,不一定有接口。但可以通过spring.aop.proxy-target-class=false切回JDK代理”
五、如何避免动态代理的坑?
-
内部方法调用失效问题
在目标类中A方法直接调用B方法,B方法的增强会失效!因为内部调用不走代理对象 → 解决方案:通过AopContext获取当前代理对象 -
代理对象类型转换异常
JDK代理对象转实现类会报ClassCastException
→ 建议:始终面向接口编程 -
CGLIB代理导致Bean拷贝失败
部分序列化工具无法处理CGLIB生成的类
→ 解决方案:配置@Configuration(proxyBeanMethods=false)
最后的小福利
如果大家准备系统性刷面试题,强烈推荐 面试鸭 的会员题库。覆盖最新大厂真题和动态代理等源码解析题,通过面试鸭返利网找我购买可返利25元,相当于75折入手!

理解AOP动态代理的两种方式,不仅是为了面试,更能帮助我们写出更优雅的代码。遇到复杂问题,想想代理对象在背后默默做了多少事,是不是瞬间通透了呢?


