在一个JAVA程序里面,在不重启该程序的情况下如何加载一个类.
已经解决对类的非静态属性|方法的加载,但对于静态的属性,方法有没有办法重新装载到内存.
/曾想过清理该类的内存空间,包括堆和栈空间,然后利用反射进行加载
各位有没有好点子可以实现对静态方法属性的加载?
谢谢-------------->

解决方案 »

  1.   

    Class.forName("className");
    试试
      

  2.   

    在不重启该程序的情况下如何加载一个类我有点没明白
    1 如果这个类曾经加载过,那么你再次加载是不可能的,除非你自定义了ClassLoader
    2 如果你没有加载过,那么你的代码在使用到这个类的时候,java会自动加载这个class. java的机制就是动态加载的,用不到的类是不会提前加载。
    3 如果你使用了字符串来表示类,那么2楼的方式可以。
      

  3.   

    我认为是Class类的forName()方法
      

  4.   

    我觉得楼主想实现的是, 这个类在程序的生命周期内加载过, 然后想通过一种方式彻底的从内存中清除掉,然后从新加载进来。 对不?我的理解是没戏, 因为你不知道JAVA虚拟机的垃圾回收是如果进行的,没法像C++那样主动的释放内存。
      

  5.   

    参看OSGi规范实现(knopfierfish, Equinox, Felix, etc....)
      

  6.   

    谢谢各位的回答,
    3楼的朋友说自定义classloader,,,请问应该怎么去实现该classloader才能做到重新加载到静态的属性,方法
    6楼的朋友,我曾经有这样想过...是否会有其它的办法实现这个功能至于其他说的class.forName(""),是可以重新加载到类的非静态属性和方法,但静态的方法就不行了.....
    不知各位是否还有其它好的办法来实现这一功能
      

  7.   

    你这个是要自己实现jvm了。sun的HotSpot Jvm实现了这种热替换技术。但还是有许多问题。比方你的这个类已经有实例存在了,你重新加载类,原来的实例怎么处理?如果增加一个方法或者属性,这个类处于继承体系的最下端还好弄,但如果是处于继承体系上层的呢?还有实例之间的引用关系怎么处理?
    sun的这个HotSpot 技术如果遇到这些问题一般都是要求重新启动jvm的。
      

  8.   

    11楼的朋友回答得很好,这确实是个问题.稍后研究HotSpot后再考虑此类问题.
    谢谢各位的回答
      

  9.   

    俺正在做一个jdbc的工具,用来访问db。
    只要是支持jdbc的数据都可以访问。
    所以要用到classloader,而不是class.forname()。
    因为这个工具启动时,程序并不知道classes12.zip或者odbcjdbc等在哪里?
    这些包不在classpath,所以class.forname是肯定访问不到。
    要动态加载,就用classloader,或者3楼的自己实现一个classloader。
      

  10.   

    楼主是想重新初使化一个已经加载的类吧, 包括类的静态属性与静态块试下这个代码   ClassLoader cl = new URLClassLoader(((URLClassLoader)ClassLoader.getSystemClassLoader()).getURLs(), ClassLoader.getSystemClassLoader().getParent());
       Class clazz = cl.loadClass("className");
      

  11.   

    1 如果这个类曾经加载过,那么你再次加载是不可能的,除非你自定义了ClassLoader 
    2 如果你没有加载过,那么你的代码在使用到这个类的时候,java会自动加载这个class. java的机制就是动态加载的,用不到的类是不会提前加载。 
    3 如果你使用了字符串来表示类,那么2楼的方式可以。
      

  12.   

    看了半天原来是要重新加载class...
    什么场合会有这种需求?
      

  13.   

    听说java反射机制中有提到,
    有兴趣的话可以看看,forName是其中方法之一
      

  14.   

    能不能像C++那样 封装DLL之类的冬冬 加载 我是学C++的
      

  15.   

    以前写过一个,MyClassLoader 是网上找的
    package demo;import java.io.BufferedInputStream;
    import java.io.ByteArrayOutputStream;
    import java.io.File;
    import java.io.FileInputStream;/**
     * 
     * @author dingwy
     *
     */
    public class MyClassLoader extends ClassLoader {  
     private String basepath; public MyClassLoader(String basepath) {
      this.basepath = basepath;
     } public MyClassLoader(ClassLoader parent, String basepath) {
      super(parent);
      this.basepath = basepath;
     } public Class findClass(String className) throws ClassNotFoundException {
      byte classData[];
      classData = getTypeFromBasePath(className);
      if (classData == null) {  }
      return defineClass(className, classData, 0, classData.length);
     } public byte[] getTypeFromBasePath(String typeName) {
      FileInputStream fis = null;
      String fileName = basepath + File.separatorChar + typeName.replace('.', File.separatorChar)
        + ".class";
      try {
       fis = new FileInputStream(fileName);
      } catch (Exception e) {
       e.printStackTrace();
       return null;
      }
      BufferedInputStream bis = new BufferedInputStream(fis);
      ByteArrayOutputStream out = new ByteArrayOutputStream();
      try {
       int c = bis.read();
       while (c != -1) {
        out.write(c);
        c = bis.read();
       }
      } catch (Exception e) {
       e.printStackTrace();
       return null;
      }
      return out.toByteArray();
     }
    }
    下边这样调用    MyClassLoader mc = new MyClassLoader(aClassPath);
        Class c = mc.findClass("pack1.pack2.RobotOne"); //[重新]加载类
        Object robot = c.newInstance(); //定义对象
        Method m = c.getMethod("dance", null); //获得方法
        m.invoke(robot, new Object[] {}); //初始化对象,调用的默认构造函数
        String sActions = robot.toString(); //执行对象方法
    有一个问题一直不明白,就是类RobotOne有一个父类Robot,在这里没办法像(Robot)robot这样把它转型成Robot类型,转型会出现class case异常,所以在这里也只能调用一下Object的toString方法.希望谁能帮忙解决一下.
      

  16.   

        m.invoke(robot, new Object[] {}); //初始化对象,调用的默认构造函数>>并且执行方法m