转自:http://blog.csdn.net/mousebaby808/article/details/31788325

概述

  诸如tomcat这样的服务器,在启动的时候会加载应用程序中lib目录下的jar文件以及classes目录下的class文件,另外像spring这类框架,也可以根据指定的路径扫描并加载指定的类文件,这个技术可以实现一个容器,容纳各类不同的子应用。
  Java类由于需要加载和编译字节码,动态加载class文件较为麻烦,不像C加载动态链接库只要一个文件名就可以搞定,但JDK仍提供了一整套方法来动态加载jar文件和class文件。
 

动态加载jar文件

  1. // 系统类库路径
  2. File libPath = new File(jar文件所在路径);
  3. // 获取所有的.jar和.zip文件
  4. File[] jarFiles = libPath.listFiles(new FilenameFilter() {
  5. public boolean accept(File dir, String name) {
  6. return name.endsWith(".jar") || name.endsWith(".zip");
  7. }
  8. });
  9. if (jarFiles != null) {
  10. // 从URLClassLoader类中获取类所在文件夹的方法
  11. // 对于jar文件,可以理解为一个存放class文件的文件夹
  12. Method method = URLClassLoader.class.getDeclaredMethod("addURL", URL.class);
  13. boolean accessible = method.isAccessible();     // 获取方法的访问权限
  14. try {
  15. if (accessible == false) {
  16. method.setAccessible(true);     // 设置方法的访问权限
  17. }
  18. // 获取系统类加载器
  19. URLClassLoader classLoader = (URLClassLoader) ClassLoader.getSystemClassLoader();
  20. for (File file : jarFiles) {
  21. URL url = file.toURI().toURL();
  22. try {
  23. method.invoke(classLoader, url);
  24. LOG.debug("读取jar文件[name={}]", file.getName());
  25. } catch (Exception e) {
  26. LOG.error("读取jar文件[name={}]失败", file.getName());
  27. }
  28. }
  29. } finally {
  30. method.setAccessible(accessible);
  31. }
  32. }

动态加载class文件

  1. // 设置class文件所在根路径
  2. // 例如/usr/java/classes下有一个test.App类,则/usr/java/classes即这个类的根路径,而.class文件的实际位置是/usr/java/classes/test/App.class
  3. File clazzPath = new File(class文件所在根路径);
  4. // 记录加载.class文件的数量
  5. int clazzCount = 0;
  6. if (clazzPath.exists() && clazzPath.isDirectory()) {
  7. // 获取路径长度
  8. int clazzPathLen = clazzPath.getAbsolutePath().length() + 1;
  9. Stack<File> stack = new Stack<>();
  10. stack.push(clazzPath);
  11. // 遍历类路径
  12. while (stack.isEmpty() == false) {
  13. File path = stack.pop();
  14. File[] classFiles = path.listFiles(new FileFilter() {
  15. public boolean accept(File pathname) {
  16. return pathname.isDirectory() || pathname.getName().endsWith(".class");
  17. }
  18. });
  19. for (File subFile : classFiles) {
  20. if (subFile.isDirectory()) {
  21. stack.push(subFile);
  22. } else {
  23. if (clazzCount++ == 0) {
  24. Method method = URLClassLoader.class.getDeclaredMethod("addURL", URL.class);
  25. boolean accessible = method.isAccessible();
  26. try {
  27. if (accessible == false) {
  28. method.setAccessible(true);
  29. }
  30. // 设置类加载器
  31. URLClassLoader classLoader = (URLClassLoader) ClassLoader.getSystemClassLoader();
  32. // 将当前类路径加入到类加载器中
  33. method.invoke(classLoader, clazzPath.toURI().toURL());
  34. } finally {
  35. method.setAccessible(accessible);
  36. }
  37. }
  38. // 文件名称
  39. String className = subFile.getAbsolutePath();
  40. className = className.substring(clazzPathLen, className.length() - 6);
  41. className = className.replace(File.separatorChar, '.');
  42. // 加载Class类
  43. Class.forName(className);
  44. LOG.debug("读取应用程序类文件[class={}]", className);
  45. }
  46. }
  47. }
  48. }

  完成上述两步操作后,即可使用Class.forName来加载jar中或.class文件包含的Java类了。

Java_Java中动态加载jar文件和class文件的更多相关文章

  1. [转载] Java中动态加载jar文件和class文件

    转载自http://blog.csdn.net/mousebaby808/article/details/31788325 概述 诸如tomcat这样的服务器,在启动的时候会加载应用程序中lib目录下 ...

  2. 【Android】Android动态加载Jar、APK的实现

    本文介绍Android中动态加载Jar.APK的实现.而主要用到的就是DexClassLoader这个类.大家都知道Android和普通的Java虚拟机有差别,它只能加载经过处理的dex文件.而加载这 ...

  3. Java从Jar文件中动态加载类

    动态加载jar包,在实际开发中经常会需要用到,尤其涉及平台和业务的关系的时候,业务逻辑部分可以独立出去交给业务方管理,业务方只需要提供jar包,就能在平台上运行. 下面通过一个实例来直观演示: 第一: ...

  4. Java动态加载jar及class文件

    经常碰到需要动态加载jar及class文件的场景.Java类由于需要加载和编译字节码,动态加载class文件较为麻烦,但JDK仍提供了一整套方法来动态加载jar文件和class文件. 一.动态加载ja ...

  5. java动态加载jar文件

    public static void main(String[] args) throws IllegalAccessException, IllegalArgumentException, Invo ...

  6. Android动态加载jar/dex

    前言 在目前的软硬件环境下,Native App与Web App在用户体验上有着明显的优势,但在实际项目中有些会因为业务的频繁变更而频繁的升级客户端,造成较差的用户体验,而这也恰恰是Web App的优 ...

  7. Android动态加载jar、apk的实现

    前段时间到阿里巴巴参加支付宝技术分享沙龙,看到支付宝在Android使用插件化的技术,挺好奇的.正好这几天看到了农民伯伯的相关文章,因此简单整理了下,有什么错误希望大神指正. 核心类 1.1     ...

  8. java动态加载jar包,并运行其中的类和方法

    动态加载jar包,在实际开发中经常会需要用到,尤其涉及平台和业务的关系的时候,业务逻辑部分可以独立出去交给业务方管理,业务方只需要提供jar包,就能在平台上运行. 下面通过一个实例来直观演示: 第一: ...

  9. 为不同分辨率单独做样式文件,在页面头部用js判断分辨率后动态加载定义好的样式文件

    为不同分辨率单独做样式文件,在页面头部用js判断分辨率后动态加载定义好的样式文件.样式文件命名格式如:forms[_屏幕宽度].css,样式文件中只需重新定义文本框和下拉框的宽度即可. 在包含的头文件 ...

随机推荐

  1. sdut 2610:Boring Counting(第四届山东省省赛原题,划分树 + 二分)

    Boring Counting Time Limit: 3000ms   Memory limit: 65536K  有疑问?点这里^_^ 题目描述     In this problem you a ...

  2. c++ 的 static_cast

    http://www.cnblogs.com/pigerhan/archive/2013/02/26/2933590.html #include "Person.h" #inclu ...

  3. .NET NLog 详解(一)

    安装NLog NLog 的源代码托管在Github 上,一般的人直接使用NuGet就可以了. 这里我们选择安装NLog.Config.当然最方便的还是直接使用命令行: Install-Package ...

  4. win10 Edge浏览器一打开就闪退崩溃的解决思路

    故障现象:从Win7.Win8.1升级到Win10,或是使用Win10一段时间后,发现Edge浏览器打开一到两秒就闪退,崩溃无法打开.解决方案: 1.尝试清理: C:\Users\Administra ...

  5. ok6410按键中断编程,linux按键裸机

    6410按键中断编程 一.流程分析 外部中断控制寄存器(s3c6410x  359页) 1.EINTxCONy: 外部中断组x的第y个控制器.这个就是设置中断的触发方式.有5种触发方式. 2.EINT ...

  6. Serializable序列化对象

    Serializable序列化对象发送: Intent intent = new Intent(); intent.setClass(mContext, HomeDetailReportActivit ...

  7. hdu 5833 Zhu and 772002 高斯消元

    Zhu and 772002 Problem Description Zhu and 772002 are both good at math. One day, Zhu wants to test ...

  8. javase基础笔记1——简介和发展

    软件分为 系统软件 windows linux类 (unix)mac(麦金塔).数据库管理系统 unix linux 开源os(open source) 免费 开放 free os operation ...

  9. ios程序后台运行设置(不是太懂)

    文一 我从苹果文档中得知,一般的应用在进入后台的时候可以获取一定时间来运行相关任务,也就是说可以在后台运行一小段时间. 还有三种类型的可以运行在后以, 1.音乐 2.location 3.voip 文 ...

  10. 通讯录(ios自带有界面)

    1.添加AddressBookUI.framework框架 2控制器中实现 #import "ViewController.h" #import <AddressBookUI ...