Java代理-动态字节码生成代理的5种方式

本文详细探讨了Java代理模式的局限,引出动态代理的必要性。文章介绍了AspectJ如何在编译期生成静态代理,接着讨论了JDK动态代理的工作原理及应用。此外,还讲解了利用cglib、自定义类加载器以及自定义字节码转换器进行动态字节码生成的方法,为理解Java动态代理提供了全面的视角。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

上篇讲到了代理模式出现的原因,实现方式以及跟其他相似设计模式的区别。传送门@_@ http://blog.youkuaiyun.com/wonking666/article/details/79497547

1.静态代理的不足

设计模式里面的代理模式,代理类是需要手动去写的。但是手写代理的问题颇多

1.如果不同类型的目标对象需要执行同样一套代理的逻辑,比如说在方法调用前后打印参数和结果,那么仍然需要为每一个类型写一个代理类,将会产生大量的样板代码,书写起来非常枯燥

2.一个类中会有多个方法,对于不需要拦截的方法,我们还是要手动调一下目标对象对应的方法,虽然只有一行代码,但写多了还是感觉蠢蠢哒

3.还有,手写的代理类是静态代理,编译之后就代码就定死了,没办法做到动态的变化,缺少一些灵动


2.对现存问题的思考

回想我们使用代理类最初的目的,就只是为了拦截某个方法的调用,在其前后执行一些额外逻辑,额外逻辑和目标方法并不具有强关联。方法调用会形成一个调用栈,可以把代理想象为是在这个栈上切了一刀,在切口上做的逻辑,我们叫切面逻辑

于是聪明的程序员想到,将纯净的切面逻辑抽出来,再定义一套切入规则,然后让工具自动生成代理类,岂不是美滋滋

所以说代理几乎天生是用来做切面的,二者有着剪不断理还乱的关系

PS: 从分析来看,AOP只需要关注3点即可:切谁?什么时候切?在切口上做什么?

最讨厌那些整一大套花里胡哨的理论东西了,什么Joinpoint,Pointcut,Advice,Before/After/Around Advice,取的名字这么不形象,故作高深只会误导吃瓜群众,哼,我掀了你的小板凳 (╯—﹏—)╯(┷━━━┷


3.如何自动生成代理

我们知道,一个类从编写,到运行时调用,中间大概会经过这几个步骤


所以生成代理可以有三个思路,一,在编译期修改源代码;二,在字节码加载前修改字节码;三,在字节码加载后动态创建代理类的字节码


类别 机制 原理 优点 缺点 技术
静态AOP 静态织入 在编译期,切面直接以字节码的形式编译到目标字节码文件中 对系统无性能影响 灵活性不够 AspectJ
动态AOP 动态代理 在运行期,目标类加载后,为接口动态生成代理类,将切面植入到代理类中 相对于静态AOP更加灵活 切入的关注点需要实现接口。对系统有一点性能影响 JDK dynamic proxy
动态字节码生成 在运行期,目标类加载后,动态构建字节码文件生成目标类的子类,将切面逻辑加入到子类中   没有接口也可以织入 扩展类的实例方法为final时,则无法进行织入 cglib
自定义类加载器 在运行期,目标加载前,将切面逻辑加到目标字节码里   可以对绝大部分类进行织入 代码中如果使用了其他类加载器,则这些类将不会被织入  
字节码转换 在运行期,所有类加载器加载字节码前,前进行拦截   可以对所有类进行织入    


4.AspectJ生成静态代理

AspectJ 是 Java 语言的一个 AOP 实现,其主要包括两个部分:第一个部分定义了如何表达、定义 AOP 编程中的语法规范,通过这套语言规范,我们可以方便地用 AOP 来解决 Java 语言中存在的交叉关注点问题;另一个部分是工具部分,包括编译器、调试工具等

下载、安装 AspectJ 比较简单,读者登录 AspectJ 官网(http://www.eclipse.org/aspectj),即可下载到一个可执行的 JAR 包,使用 java -jar aspectj-1.x.x.jar 命令、多次单击“Next”按钮即可成功安装 AspectJ

AspectJ 的用法非常简单,就像我们使用 JDK 编译、运行 Java 程序一样,下面是一个简单的示例


编写一个POJO业务类

public class HelloAspectJ {
    public void sayHello() {
        System.out.println("Hello AspectJ");
    }

    public static void main(String[] args)
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值