当前位置: 首页 > news >正文

番禺做网站成人编程培训机构排名前十

番禺做网站,成人编程培训机构排名前十,手机版网站建设开发,兰州网站建设100ProxyGenerator是JDK-sun包下提供的用于生成动态代理类信息的类,其唯一向外透出的是其静态方法-generateProxyClass(…)。 public class ProxyGenerator { ... }学习本篇文章,就是想学习ProxyGenerator如何生成代理类信息的过程。 一、唯一入口-公开静…

ProxyGenerator是JDK-sun包下提供的用于生成动态代理类信息的类,其唯一向外透出的是其静态方法-generateProxyClass(…)。

public class ProxyGenerator {
...
}

学习本篇文章,就是想学习ProxyGenerator如何生成代理类信息的过程。

一、唯一入口-公开静态方法

ProxyGenerator仅提供了一个公开静态方法-方法名为generateProxyClass。从方法入参看,创建代理类信息需传入的参数包括代理类全限定名、代理类实现的接口数组,访问权限标识。实际上,generateProxyClass还有一个重载方法,默认访问权限标识为:public final

public static byte[] generateProxyClass(final String name,Class<?>[] interfaces,int accessFlags){// 根据必须参数实例化ProxyGenerator类ProxyGenerator gen = new ProxyGenerator(name, interfaces, accessFlags);// ProxyGenerator对象生成class文件final byte[] classFile = gen.generateClassFile();// 是否要保存生成的class文件if (saveGeneratedFiles) {java.security.AccessController.doPrivileged(new java.security.PrivilegedAction<Void>() {public Void run() {try {int i = name.lastIndexOf('.');Path path;if (i > 0) {Path dir = Paths.get(name.substring(0, i).replace('.', File.separatorChar));Files.createDirectories(dir);path = dir.resolve(name.substring(i+1, name.length()) + ".class");} else {path = Paths.get(name + ".class");}Files.write(path, classFile);return null;} catch (IOException e) {throw new InternalError("I/O exception saving generated file: " + e);}}});}return classFile;
}
  • ProxyGenerator就只提供了一个私有构造方法,内部使用
  • saveGeneratedFiles:根据"sun.misc.ProxyGenerator.saveGeneratedFiles"系统属性值来选择是否保存代理class文件,默认不保存。
  • 保存文件相关日后可以总结下。
    所以,其实重点就在ProxyGenerator对象的generateClassFile()方法。

二、生成代理类流程

下为ProxyGenerator#generateClassFile()生成具体代理类的代码及注释:

private byte[] generateClassFile() {/* ============================================================* 第一步:组装所有的代理方法, 根据代理签名为Key缓存在proxyMethods属性中。*//** 1.1 向代理类中增加Object类的必须重写的方法。* 这里增加的方法比较早,因此会优先于实现接口的重复方法。*/addProxyMethod(hashCodeMethod, Object.class);addProxyMethod(equalsMethod, Object.class);addProxyMethod(toStringMethod, Object.class);/** 1.2 将接口中的方法信息添加到代理类中。* 注意:前面的方法优先级高于后面接口重复方法。*/for (Class<?> intf : interfaces) {for (Method m : intf.getMethods()) {addProxyMethod(m, intf);}}/** 1.3 校验多个相同方法签名的方法返回值是否兼容*/for (List<ProxyMethod> sigmethods : proxyMethods.values()) {checkReturnTypes(sigmethods);}/* ============================================================* 第二步:组装代理类所有的属性和方法信息,包括构造方法、重写方法、静态初始化方法*/try {// 2.1 增加构造方法methods.add(generateConstructor());for (List<ProxyMethod> sigmethods : proxyMethods.values()) {for (ProxyMethod pm : sigmethods) {// add static field for method's Method object// 2.2 组装代理类所有的属性-指向方法的属性fields.add(new FieldInfo(pm.methodFieldName,"Ljava/lang/reflect/Method;",ACC_PRIVATE | ACC_STATIC));// generate code for proxy method and add it// 2.3 组装代理类所有的重写方法methods.add(pm.generateMethod());}}// 2.4 组装代理类的惊天初始化方法methods.add(generateStaticInitializer());} catch (IOException e) {throw new InternalError("unexpected I/O Exception", e);}if (methods.size() > 65535) {  // 限制方法和属性的个数限制<=65535throw new IllegalArgumentException("method limit exceeded");}if (fields.size() > 65535) {throw new IllegalArgumentException( "field limit exceeded");}/* ============================================================* Step 3: Write the final class file.*//** Make sure that constant pool indexes are reserved for the* following items before starting to write the final class file.* 确保常量池中包含类名、父类名、实现的所有接口名* 常量池来源:类声明信息、方法信息【前面应添加进去】*/cp.getClass(dotToSlash(className));cp.getClass(superclassName);for (Class<?> intf: interfaces) {cp.getClass(dotToSlash(intf.getName()));}/** 常量池只为仅读,不再允许写*/cp.setReadOnly();ByteArrayOutputStream bout = new ByteArrayOutputStream();DataOutputStream dout = new DataOutputStream(bout);try {/** 按照JVM规范写类文件信息*/// u4 magic;dout.writeInt(0xCAFEBABE);// u2 minor_version;dout.writeShort(CLASSFILE_MINOR_VERSION);// u2 major_version;dout.writeShort(CLASSFILE_MAJOR_VERSION);cp.write(dout);             // (write constant pool)// u2 access_flags;dout.writeShort(accessFlags);// u2 this_class;dout.writeShort(cp.getClass(dotToSlash(className)));// u2 super_class;dout.writeShort(cp.getClass(superclassName));// u2 interfaces_count;dout.writeShort(interfaces.length);// u2 interfaces[interfaces_count];for (Class<?> intf : interfaces) {dout.writeShort(cp.getClass(dotToSlash(intf.getName())));}// u2 fields_count;dout.writeShort(fields.size());// field_info fields[fields_count];for (FieldInfo f : fields) {f.write(dout);}// u2 methods_count;dout.writeShort(methods.size());// method_info methods[methods_count];for (MethodInfo m : methods) {m.write(dout);}// u2 attributes_count;dout.writeShort(0); // (no ClassFile attributes for proxy classes)} catch (IOException e) {throw new InternalError("unexpected I/O Exception", e);}return bout.toByteArray();
}

Class文件结构:
在这里插入图片描述

http://www.zhongyajixie.com/news/66118.html

相关文章:

  • 怎么做蒙文网站百度小说搜索热度排行榜
  • 做网站前端设计需要哪些证书国外搜索引擎网站
  • 自己做培训网站杭州推广系统
  • 泰安网站建设流程无锡网站推广公司
  • 佟年给韩商言做的网站关键词优化排名哪家好
  • 做亚马逊网站费用吗百度指数资讯指数
  • 网站seo优化主要有哪些手段有哪些平台可以发布推广信息
  • 建设银行网站查询密码设置网店代运营商
  • 衡水龙腾网站建设优化设计七年级上册语文答案
  • 程序员怎么用wordpress关键词是网站seo的核心工作
  • 泉州做网站优化价格seo长沙
  • wps2016怎么做网站app开发需要哪些技术
  • 西宁网站建设优化整站seo排名外包
  • 问卷调查网站JAVA怎么做百度外推代发排名
  • dkp网站开发百度推广
  • 网站建设确认函怎么申请建立网站
  • 天蓝色系网站设计西安网络推广公司
  • 特价手机网站建设苏州网站建设公司
  • 百度云怎么做网站空间教你免费申请个人网站
  • 海淘一号 网站 怎么做的百度上海推广优化公司
  • 莱芜网站建设案例aso关键词优化计划
  • 免费行情软件app网站大全缅甸新闻最新消息
  • 企业网站报价单正规教育培训机构
  • 中国著名的网站建设公司东莞关键词自动排名
  • 做梯子的企业网站seo推广公司哪家好
  • 做宠物食品的网站seo系统推广
  • b2b网站的一般流程seo网站优化论文
  • 《电子商务网站开发与管理》google浏览器官网入口
  • 邵阳seo网站优化排名易下拉效率
  • 潍坊企业建站系统朋友圈产品推广文案