1、publicclassRemoveMethodAdapterextendsClassAdapter{
privateStringmName;
privateStringmDesc;
public RemoveMethodAdapter(
ClassVisitorcv,StringmName,StringmDesc){
super(cv);
this.mName=mName;
this.mDesc=mDesc;
}
@Override
public MethodVisitor visitMethod(intaccess,Stringname,
Stringdesc,Stringsignature,String[]exceptions){
if(name.equals(mName)&&desc.equals(mDesc)){
//donotdelegatetonextvisitor->thisremovesthemethod
return null;
}
returncv.visitMethod(access,name,desc,signature,exceptions);
}
}
为了移除属性或者方法,你必须在visitMethod或者visitField方法中返回null.
2、
public class AddFieldAdapter extends ClassAdapter{
private int fAcc;
private String fName;
private String fDesc;
private boolean isFieldPresent;
public AddFieldAdapter(ClassVisitorcv,intfAcc,StringfName,
StringfDesc){
super(cv);
this.fAcc=fAcc;
this.fName=fName;
this.fDesc=fDesc;
}
@Override
public FieldVisitor visitField(intaccess,Stringname,Stringdesc,
Stringsignature,Objectvalue){
if(name.equals(fName)){
isFieldPresent=true;
}
returncv.visitField(access,name,desc,signature,value);
}
@Override
public void visitEnd(){
if(!isFieldPresent){
FieldVisitorfv=cv.visitField(fAcc,fName,fDesc,null,null);
if(fv!=null){
fv.visitEnd();
}
}
cv.visitEnd();
}
}
字段属性在visitEnd方法中被添加进去,
Note: infacttheonlytrulycorrectsolutionistoaddnewmembersbymaking
additionalcallsinthevisitEnd method.Indeedaclassmustnotcontain
duplicatemembers,andtheonlywaytobesurethatanewmemberis
uniqueistocompareitwithalltheexistingmembers,whichcanonly
bedoneoncetheyhaveallbeenvisited,i.e.inthe visitEnd method.
翻译:实际上,最好的方式是通过visitEnd方法添加新字段,因为一个类不能有重复的字段名称,只有在所有的字段都被加载后,我们才能判断新增加的字段是否重复!
3、ClassAdapter就是封装了一遍ClassWriter,而ClassWriter又继承了ClassVisitor.
4、ClassWritercw= newClassWriter(0);
cw.visit(V1_5,ACC_PUBLIC+ACC_ABSTRACT+ACC_INTERFACE,
"pkg/Comparable",null,"java/lang/Object",
newString[]{"pkg/Mesurable"});
cw.visitField(ACC_PUBLIC+ACC_FINAL+ACC_STATIC,"LESS","I",
null,newInteger(-1)).visitEnd();
cw.visitField(ACC_PUBLIC+ACC_FINAL+ACC_STATIC,"EQUAL","I",
null,newInteger(0)).visitEnd();
cw.visitField(ACC_PUBLIC+ACC_FINAL+ACC_STATIC,"GREATER","I",
null,newInteger(1)).visitEnd();
cw.visitMethod(ACC_PUBLIC+ACC_ABSTRACT,"compareTo",
"(Ljava/lang/Object;)I",null,null).visitEnd();
cw.visitEnd();
byte[]b=cw.toByteArray();
等价于:
packagepkg;
publicinterfaceComparableextendsMesurable{
intLESS=-1;
intEQUAL=0;
intGREATER=1;
intcompareTo(Objecto);
}