资讯专栏INFORMATION COLUMN

Java知识点总结(动态字节码操作-Javassist介绍)

godruoyi / 1260人阅读

摘要:知识点总结动态字节码操作介绍知识点总结动态字节码操作运行时操作字节码可以让我们实现如下功能动态生成新的类动态改变某个类的结构添加删除修改新的属性方法常见的字节码操作类库,这是的项目的一部分。

Java知识点总结(动态字节码操作-Javassist介绍)

@(Java知识点总结)[Java, 动态字节码操作]

运行时操作字节码可以让我们实现如下功能:

动态生成新的类

动态改变某个类的结构(添加/删除/修改 新的属性/方法)

java常见的字节码操作类库
BCEL

Byte Code Engineering Library (BCEL) ,这是 Apache Software Foundation 的 Jakarta 项目的一部分。 BCEL 是 Java classworking 广泛 使用的一种 框架 , 它 可以让您深入 JVM 汇编语言进行类操作的细节。 BCEL 与 Javassist 有不同的处理字节码方法, BCEL 在实际的 JVM 指令层次上进行操作 (BCEL 拥有丰富的 JVM 指令级支持 ) 而 Javassist 所 强调 的是源代码 级别的 工作 。

ASM

是一个轻量级 java 字节码操作框架,直接涉及到 JVM 底层的操作和 指令

CGLIB(Code Generation Library)

是一个强大的,高性能,高质量的 Code

Javassist

是 一个开源的分析、编辑和创建 Java 字节码 的类库 。性能较 ASM 差,跟 cglib 差不多,但是使用简单。很多开源框架都在使用它 。

   主页:http://www.csg.ci.i.u-tokyo.ac.jp/~ chiba/javassist 

Javassist

使用Javassist需要使用javassist.jar

优势:

比反射开销小,性能高。

JAVAsist性能高于反射,低于ASM

局限性:

JDK新语法不支持(包括泛型、枚举),不支持注解修改,但可以通过底层的javasist类来解决,具体参考:javassist.bytecode.annotaion

不支持数组的初始化,如 String[]{"1","2"},除非只有数组的容量为1

不支持内部类和匿名类

不支持 continue 和 break 表达式。

对于继承关系,有些不支持 。例如:- class A{} - class B extends A{} - class C enxends B {}

应用场景:

AOP:

给一个类增加新的方法

给一段语句前面和后面(before/after/around)动态的加代码

Reflection:起到类似反射的效果


javassist 的最外层的 API 和 JAVA 的反射包中的 API 颇为类似 。

它主要由 CtClass , CtMethod, ,以及 CtField 几个类组成。用以执行和 JDK 反射 API 中 java.lang.Class , java.lang.reflect.Method , java.lang.reflect.Method .Field 相同的 操作 。

方法操作

修改已有方法的方法体体(插入代码到已有方法体)

新增方法 删除方法

占位符参数介绍:

示例:

import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtConstructor;
import javassist.CtField;
import javassist.CtMethod;
/**
 * 创建一个新的类
 * @author Administrator
 *
 */
public class Test10 {
  public static void main(String[] args) throws Exception {
    ClassPool pool = ClassPool.getDefault(); // 类池
    CtClass class1 = pool.makeClass("com.gs.Emp");
    
    //创建属性
    CtField f1 = CtField.make("private int num;", class1);
    CtField f2 = CtField.make("private String name;", class1);
    class1.addField(f1);
    class1.addField(f2);
    
    //创建方法
    CtMethod setName = CtMethod.make("public void setName(String name){this.name = name;}", class1);
    CtMethod getName = CtMethod.make("public String getName(){return name;}", class1);
    class1.addMethod(setName);
    class1.addMethod(getName);
    
    //添加构造器。  如果是带参构造器,需要传递参数类型,基本数据类型用CtClass获取,引用类型,需要用pool获取
    CtConstructor constructor = new CtConstructor(new CtClass[]{CtClass.intType,pool.get("java.lang.String")}, class1);
    constructor.setBody("{this.num = num;this.name = name;}"); //构造器的方法体
    
    class1.writeFile("E:/myjava"); //将上面写好的类,写入到这个工作空间中
    
    System.out.println("生成类成功!");
  }
}

执行结果:
生成类成功!


使用反编译工具xjad打开:

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/71627.html

相关文章

  • Java识点总结动态字节操作-Javassist的API使用)

    摘要:因此,若想对对象进行修改,必须对其进行解冻,通过方法进行生成一个方法生成一个方法通过反射调用生成的方法方法体前面和后面加执行语句方法体前面通过反射调用生成的方法张三生成属性和方法获取属性生成构造器可以在构造器前后加代码注解操作 Java知识点总结(动态字节码操作-Javassist的API使用) @(Java知识点总结)[Java, 动态字节码操作] 参考文章: 传送 操作示例: pu...

    U2FsdGVkX1x 评论0 收藏0
  • Java动态编程初探

    摘要:动态编程使用场景通过配置生成代码,减少重复编码,降低维护成本。动态生成字节码操作字节码的工具有,其中有两个比较流行的,一个是,一个是。 作者简介 传恒,一个喜欢摄影和旅游的软件工程师,先后从事饿了么物流蜂鸟自配送和蜂鸟众包的开发,现在转战 Java,目前负责物流策略组分流相关业务的开发。 什么是动态编程 动态编程是相对于静态编程而言的,平时我们讨论比较多的静态编程语言例如Java, 与动态...

    赵连江 评论0 收藏0
  • Android 性能监控系列一(原理篇)

    摘要:全称应用性能管理监控后面我会通过一系列的文章来介绍的原理框架设计与实现等等。在应用构建期间,通过修改字节码的方式来进行字节码插桩就是实现自动化的方案之一。 showImg(https://segmentfault.com/img/bVbbRX6?w=1995&h=1273); 欢迎关注微信公众号:BaronTalk,获取更多精彩好文! 一. 前言 性能问题是导致 App 用户流失的罪魁...

    yacheng 评论0 收藏0
  • Java 动态性(4) - 字节操作

    摘要:字节码操作动态性的两种常见实现方式字节码操作反射运行时操作字节码可以让我们实现如下功能动态生成新的类动态改变某个类的结构添加删除修改新的属性方法优势比反射开销小性能高性能高于反射低于常见的字节码操作类库这是的项目的一部分是广泛使用的一种框它 1.字节码操作 JAVA动态性的两种常见实现方式字节码操作 反射 运行时操作字节码可以让我们实现如下功能动态生成新的类 动态改变某个类的结构(...

    CoderStudy 评论0 收藏0
  • 深入字节 -- 计算方法执行时间

    摘要:什么是字节码程序通过编译之后生成文件就是字节码集合正是有这样一种中间码字节码,使得等函数语言只用实现一个编译器即可运行在上。 什么是字节码? java程序通过javac编译之后生成文件.class就是字节码集合,正是有这样一种中间码(字节码),使得scala/groovy/clojure等函数语言只用实现一个编译器即可运行在JVM上。看看一段简单代码。 public long ...

    娣辩孩 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<