网站开发有哪些技术wordpress新建音乐界面
news/
2025/10/6 17:56:56/
文章来源:
网站开发有哪些技术,wordpress新建音乐界面,网站建设存在问题整改报告,seo外包网络公司转载自 ClassLoader 详解及用途 ClassLoader主要对类的请求提供服务#xff0c;当JVM需要某类时#xff0c;它根据名称向ClassLoader要求这个类#xff0c;然后由ClassLoader返回这个类的class对象。
1.1 几个相关概念ClassLoader负责载入系统的所有Resources#xff08;…转载自 ClassLoader 详解及用途 ClassLoader主要对类的请求提供服务当JVM需要某类时它根据名称向ClassLoader要求这个类然后由ClassLoader返回这个类的class对象。
1.1 几个相关概念ClassLoader负责载入系统的所有ResourcesClass文件来自网络的字节流等通过ClassLoader从而将资源载入JVM
每个class都有一个reference指向自己的ClassLoader。Class.getClassLoader() array的ClassLoader就是其元素的ClassLoader若是基本数据类型则这个array没有ClassLoader 1.2 主要方法和工作过程Java1.1及从前版本中ClassLoader主要方法
Class loadClass( String name, boolean resolve ); ClassLoader.loadClass() 是 ClassLoader 的入口点 defineClass 方法是 ClassLoader 的主要诀窍。该方法接受由原始字节组成的数组并把它转换成 Class 对象。原始数组包含如从文件系统或网络装入的数据。 findSystemClass 方法从本地文件系统装入文件。它在本地文件系统中寻找类文件如果存在就使用 defineClass 将原始字节转换成 Class 对象以将该文件转换成类。当运行 Java 应用程序时这是 JVM 正常装入类的缺省机制。 resolveClass可以不完全地不带解析装入类也可以完全地带解析装入类。当编写我们自己的 loadClass 时可以调用 resolveClass这取决于 loadClass 的 resolve 参数的值 findLoadedClass 充当一个缓存当请求 loadClass 装入类时它调用该方法来查看 ClassLoader 是否已装入这个类这样可以避免重新装入已存在类所造成的麻烦。应首先调用该方法 一般load方法过程如下 调用 findLoadedClass 来查看是否存在已装入的类。 如果没有那么采用某种特殊的神奇方式来获取原始字节。通过IO从文件系统来自网络的字节流等 如果已有原始字节调用 defineClass 将它们转换成 Class 对象。 如果没有原始字节然后调用 findSystemClass 查看是否从本地文件系统获取类。 如果 resolve 参数是 true那么调用 resolveClass 解析 Class 对象。 如果还没有类返回 ClassNotFoundException。 否则将类返回给调用程序。 1.3 委托模型自从JDK1.2以后ClassLoader做了改进使用了委托模型所有系统中的ClassLoader组成一棵树ClassLoader在载入类库时先让Parent寻找Parent找不到才自己找。
JVM在运行时会产生三个ClassLoaderBootstrap ClassLoader、Extension ClassLoader和App ClassLoader。其中Bootstrap ClassLoader是用C编写的在Java中看不到它是null。它用来加载核心类库就是在lib下的类库Extension ClassLoader加载lib/ext下的类库App ClassLoader加载Classpath里的类库三者的关系为:App ClassLoader的Parent是Extension ClassLoader而Extension ClassLoader的Parent为Bootstrap ClassLoader。加载一个类时首先BootStrap进行寻找找不到再由Extension ClassLoader寻找最后才是App ClassLoader。 将ClassLoader设计成委托模型的一个重要原因是出于安全考虑比如在Applet中如果编写了一个java.lang.String类并具有破坏性。假如不采用这种委托机制就会将这个具有破坏性的String加载到了用户机器上导致破坏用户安全。但采用这种委托机制则不会出现这种情况。因为要加载java.lang.String类时系统最终会由Bootstrap进行加载这个具有破坏性的String永远没有机会加载。 委托模型还带来了一些问题在某些情况下会产生混淆如下是Tomcat的ClassLoader结构图: Bootstrap | System | Common / Catalina Shared / Webapp1 Webapp2 ... 由 Common 类装入器装入的类决不能根据名称直接访问由 Web 应用程序装入的类。使这些类联系在一起的唯一方法是通过使用这两个类集都可见的接口。在这个例子中就是包含由 Java servlet 实现的 javax.servlet.Servlet。 如果在lib或者lib/ext等类库有与应用中同样的类那么应用中的类将无法被载入。通常在jdk新版本出现有类库移动时会出现问题例如最初我们使用自己的xml解析器而在jdk1.4中xml解析器变成标准类库load的优先级也高于我们自己的xml解析器我们自己的xml解析器永远无法找到将可能导致我们的应用无法运行。 相同的类不同的ClassLoader将导致ClassCastException异常 1.4 线程中的ClassLoader每个运行中的线程都有一个成员contextClassLoader用来在运行时动态地载入其它类可以使用方法Thread.currentThread().setContextClassLoader(...);更改当前线程的contextClassLoader来改变其载入类的行为也可以通过方法Thread.currentThread().getContextClassLoader()来获得当前线程的ClassLoader。 实际上在Java应用中所有程序都运行在线程里如果在程序中没有手工设置过ClassLoader对于一般的java类如下两种方法获得的ClassLoader通常都是同一个 this.getClass.getClassLoader() Thread.currentThread().getContextClassLoader() 方法一得到的Classloader是静态的表明类的载入者是谁方法二得到的Classloader是动态的谁执行某个线程就是那个执行者的Classloader。对于单例模式的类静态类等载入一次后这个实例会被很多程序线程调用对于这些类载入的Classloader和执行线程的Classloader通常都不同。 1.5 Web应用中的ClassLoader回到上面的例子在Tomcat里WebApp的ClassLoader的工作原理有点不同它先试图自己载入类在ContextPath/WEB-INF/...中载入类如果无法载入再请求父ClassLoader完成。 由此可得 对于WEB APP线程它的contextClassLoader是WebAppClassLoader 对于Tomcat Server线程它的contextClassLoader是CatalinaClassLoader 1.6 获得ClassLoader的几种方法可以通过如下3种方法得到ClassLoader
this.getClass.getClassLoader(); // 使用当前类的ClassLoader Thread.currentThread().getContextClassLoader(); // 使用当前线程的ClassLoader ClassLoader.getSystemClassLoader(); // 使用系统ClassLoader即系统的入口点所使用的ClassLoader。注意system ClassLoader与根ClassLoader并不一样。JVM下system ClassLoader通常为App ClassLoader 1.7 几种扩展应用用户定制自己的ClassLoader可以实现以下的一些应用
安全性。类进入JVM之前先经过ClassLoader所以可以在这边检查是否有正确的数字签名等 加密。java字节码很容易被反编译通过定制ClassLoader使得字节码先加密防止别人下载后反编译这里的ClassLoader相当于一个动态的解码器 归档。可能为了节省网络资源对自己的代码做一些特殊的归档然后用定制的ClassLoader来解档 自展开程序。把java应用程序编译成单个可执行类文件这个文件包含压缩的和加密的类文件数据同时有一个固定的ClassLoader当程序运行时它在内存中完全自行解开无需先安装 动态生成。可以生成应用其他还未生成类的类实时创建整个类并可在任何时刻引入JVM 2.1 资源载入
所有资源都通过ClassLoader载入到JVM里那么在载入资源时当然可以使用ClassLoader只是对于不同的资源还可以使用一些别的方式载入例如对于类可以直接new对于文件可以直接做IO等。 2.1 载入类的几种方法假设有类A和类BA在方法amethod里需要实例化B可能的方法有3种。对于载入类的情况用户需要知道B类的完整名字包括包名例如com.rain.B 2.1.1 使用Class静态方法 Class.forName Class cls Class.forName(com.rain.B); B b (B)cls.newInstance(); 2.1.2 使用ClassLoader /* Step 1. Get ClassLoader */ ClassLoader cl; // 如何获得ClassLoader参考1.6 /* Step 2. Load the class */ Class cls cl.loadClass(com.rain.B); // 使用第一步得到的ClassLoader来载入B /* Step 3. new instance */ B b (B)cls.newInstance(); // 有B的类得到一个B的实例 2.1.3 直接new B b new B(); 2.2 文件载入例如配置文件等假设在com.rain.A类里想读取文件夹 /com/rain/config 里的文件sys.properties读取文件可以通过绝对路径或相对路径绝对路径很简单在Windows下以盘号开始在Unix下以/开始
对于相对路径其相对值是相对于ClassLoader的因为ClassLoader是一棵树所以这个相对路径和ClassLoader树上的任何一个ClassLoader相对比较后可以找到文件那么文件就可以找到当然读取文件也使用委托模型 2.2.1 直接IO
/** * 假设当前位置是 C:/test通过执行如下命令来运行A java com.rain.A * 1. 在程序里可以使用绝对路径Windows下的绝对路径以盘号开始Unix下以/开始 * 2. 也可以使用相对路径相对路径前面没有/ * 因为我们在 C:/test 目录下执行程序程序入口点是C:/test相对路径就 * 是 com/rain/config/sys.properties * 例子中当前程序的ClassLoader是App ClassLoadersystem ClassLoader 当前的 * 程序的ClassLoader入口点是C:/test * 对于ClassLoader树如果文件在jdk lib下如果文件在jdk lib/ext下如果文件在环境变量里 * 都可以通过相对路径sys.properties找到lib下的文件最先被找到 */
File f new File(C:/test/com/rain/config/sys.properties); // 使用绝对路径
//File f new File(com/rain/config/sys.properties); // 使用相对路径
InputStream is new FileInputStream(f);
如果是配置文件可以通过java.util.Properties.load(is)将内容读到Properties里Properties默认认为is的编码是ISO-8859-1如果配置文件是非英文的可能出现乱码问题。 2.2.2 使用ClassLoader
/** * 因为有3种方法得到ClassLoader对应有如下3种方法读取文件 * 使用的路径是相对于这个ClassLoader的那个点的相对路径此处只能使用相对路径 */
InputStream is null;
is this.getClass().getClassLoader().getResourceAsStream( com/rain/config/sys.properties); //方法1
//is Thread.currentThread().getContextClassLoader().getResourceAsStream( com/rain/config/sys.properties); //方法2
//is ClassLoader.getSystemResourceAsStream(com/rain/config/sys.properties); //方法3
如果是配置文件可以通过java.util.Properties.load(is)将内容读到Properties里这里要注意编码问题。 2.2.3 使用ResourceBundle ResourceBundle bundle ResourceBundle.getBoundle(com.rain.config.sys);
这种用法通常用来载入用户的配置文件关于ResourceBunlde更详细的用法请参考其他文档 总结有如下3种途径来载入文件 1. 绝对路径 --- IO 2. 相对路径 --- IO --- ClassLoader 3. 资源文件 --- ResourceBundle 2.3 如何在web应用里载入资源在web应用里当然也可以使用ClassLoader来载入资源但更常用的情况是使用ServletContext如下是web目录结构 ContextRoot |- JSP、HTML、Image等各种文件 |- [WEB-INF] |- web.xml |- [lib] Web用到的JAR文件 |- [classes] 类文件 用户程序通常在classes目录下如果想读取classes目录里的文件可以使用ClassLoader如果想读取其他的文件一般使用ServletContext.getResource() 如果使用ServletContext.getResource(path)方法路径必须以/开始路径被解释成相对于ContextRoot的路径此处载入文件的方法和ClassLoader不同举例/WEB-INF/web.xml,/download/WebExAgent.rar
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/929569.shtml
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!