<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    敬的世界

    常用鏈接

    統(tǒng)計(jì)

    最新評(píng)論

    A Look At The Java Class Loader

    Class loading is one of the most poserful mechanisms provided by the Java Language Specification. All Java programmers should know the class loading mechanism works and what can be done to suit their needs. By understanding the class loading mechanism you can save time that would otherwise be spent on debugging ClassNotFoundException, ClassCastException . etc.

    Class Loaders

    In a Java Virtual Machine(JVM), each and every class is loaded by some instance of a java.lang.ClassLoader. The ClassLoader class is located in the java.lang.package and you can extend it to add your own functionality to class loading.

    When a new JVM is started by "java HelloWorld", the "bootstrap class loader" is responsible for loading key java classes like java.lang.Object and other runtime code into memory. The runtime classes are packaged inside jre/lib/rt.jar file. We cannot find the details of the bootstrap class loader in the java language specification, since this is a native implementation. For this reason the behavior of the bootstrap class loader will differ across JVM's.

    Maze Behind Loaders

    All class loaders are of the type java.lang.ClassLoader. Other than the bootstrap class loader all class loaders have a parent class loader. These two statements are different and are important for the correct working of any class loaders written by a developer. The most important aspect is to correctly set the parent class loader. The parent class loader for any class loader is the class loader instance that loaded that class loader.

    We have two ways to set the parent class loader:

    public class CustomClassLoader extends ClassLoader{
    ???
    ???public CustomClassLoader(){
    ??????super(CustomClassLoader.class.getClassLoader());
    ???}
    }
    or

    public class CustomClassLoader extedns ClassLoader{
    ???
    ???public CustomClassLoader(){
    ??????super(getClass().getClassLoader());
    ???}
    }

    The first constructor is the preferred one, because calling the method getClass() from within a constructor should be discouraged, since the object initialization will be complete only at the exit of the constructor code. Thus if the parent class loader is correct set, whenever a class is requested out of a ClassLoader instance using loadClass(String name) method, if it cannot find the class, it should ask the prent first. If the parent cannot find the class, the findClass(String name) method is invoked. The default implementation of findClass(String name) will throw ClassNotFoundException and developers are expected to implement this method when they subclass java.lang.ClassLoader to make custom class loaders.

    Inside the findClass(String name) method, the class loader needs to fetch the byte codes from some arbitrary source. The source may be a file system, a network URL, another application that can spit out byte codes on the fly, or any similar source that is capable of generating byte code compliant with the Java byte code specification. Once the byte code is retrieved, the method should call the defineClass() method, and the runtime is very particular about which instance of the ClassLoader is calling the method. Thus if two ClassLoader instances define byte codes from the same or different sources, the defined classes are different.

    For example, lets say I’ve a main class called MyProgram. MyProgram is loaded by the application class loader, and it created instances of two class loaders CustomClassLoader1 and CustomClassLoader2 which are capable of finding the byte codes of another class Student from some source. This means the class definition of the Student class is not in the application class path or extension class path. In such a scenario the MyProgram class asks the custom class loaders to load the Student class, Student will be loaded and Student.class will be defined independently by both CustomClassLoader1 and CustomClassLoader2. This has some serious implications in java. In case some static initialization code is put in the Student class, and if we want this code to be executed one and only once in a JVM, the code will be executed twice in the JVM with our setup, once each when the class is separately loaded by both CustomClassLoaders. If we have two instances of Student class loaded by these CustomClassLoaders say student1 and student2, then student1 and student2 are not type-compatible. In other words,

    Student student3 = (Student) student2;

    will throw ClassCastException, because the JVM sees these two as separate, distinct class types, since they are defined by different ClassLoader instances.

    The Need For Your Own Class loader

    For those who wish to control the JVM’s class loading behavior, the developers need to write their own class loader. Let us say that we are running an application and we are making use of a class called Student. Assuming that the Student class is updated with a better version on the fly, i.e. when the application is running, and we need to make a call to the updated class. If you are wondering that the bootstrap class loader that has loaded the application will do this for you, then you are wrong. Java’s class loading behavior is such that, once it has loaded the classes, it will not reload the new class. How to overcome this issue has been the question on every developers mind. The answer is simple. Write your own class loader and then use your class loader to load the classes. When a class has been modified on the run time, then you need to create a new instance of your class loader to load the class. Remember, that once you have created a new instance of your class loader, then you should make sure that you no longer make reference to the old class loader, because when two instances of the same object is loaded by different class loaders then they are treated as incompatible types.

    Writing Your Own Class loader

    The solution to control class loading is to implement custom class loaders. Any custom class loader should have java.lang.ClassLoader as its direct or distant super class. Moreover you need to set the parent class loader in the constructor. Then you have to override the findClass() method. Here is an implementation of a custom class loader.

    import java.io.DataInputStream;
    import java.io.File;
    import java.io.FileInputStream;
    import java.io.IOException;
    import java.util.Enumeration;
    import java.util.Hashtable;
    public class CustomClassLoader extends ClassLoader {
    public CustomClassLoader(){
    super(CustomClassLoader.class.getClassLoader());
    }

    public Class loadClass(String className) throws ClassNotFoundException {
    return findClass(className);
    }

    public Class findClass(String className){
    byte classByte[];
    Class result=null;
    result = (Class)classes.get(className);
    if(result != null){
    return result;
    }

    try{
    return findSystemClass(className);
    }catch(Exception e){
    }
    try{
    String classPath = ((String)ClassLoader.getSystemResource(className.replace('.',File.separatorChar)+".class").getFile()).substring(1);
    classByte = loadClassData(classPath);
    result = defineClass(className,classByte,0,classByte.length,null);
    classes.put(className,result);
    return result;
    }catch(Exception e){
    return null;
    }
    }

    private byte[] loadClassData(String className) throws IOException{

    File f ;
    f = new File(className);
    int size = (int)f.length();
    byte buff[] = new byte[size];
    FileInputStream fis = new FileInputStream(f);
    DataInputStream dis = new DataInputStream(fis);
    dis.readFully(buff);
    dis.close();
    return buff;
    }

    private Hashtable classes = new Hashtable();
    }

    Here is how to use the CustomClassLoader.

    public class CustomClassLoaderTest {

    public static void main(String [] args) throws Exception{
    CustomClassLoader test = new CustomClassLoader();
    test.loadClass(“com.test.HelloWorld”);
    }
    }

    Summary

    Many J2EE application servers have a “ hot deployment ” capability, where we can reload an application with a new version of class definition, without bringing the server VM down. Such application servers make use of custom class loaders. Even if we don’t use an application server, we can create and use custom class loaders to fine-control class loading mechanisms in our Java applications. So have fun with custom loaders

    posted on 2008-10-04 16:59 picture talk 閱讀(485) 評(píng)論(2)  編輯  收藏

    評(píng)論

    # re: A Look At The Java Class Loader 2008-12-03 16:41 gfdg

    help in executing the given code
    i am unable to compile the code
    i am getting error message as
      回復(fù)  更多評(píng)論   

    # re: A Look At The Java Class Loader 2009-10-08 01:30 picture talk

    @gfdg
    hi, what's wrong with it ? can you tell what the error message is ?  回復(fù)  更多評(píng)論   


    只有注冊(cè)用戶登錄后才能發(fā)表評(píng)論。


    網(wǎng)站導(dǎo)航:
     
    主站蜘蛛池模板: 亚洲日产2021三区在线 | 亚洲成人福利网站| 暖暖免费日本在线中文| 亚洲男人的天堂www| 国产免费区在线观看十分钟| 久99精品视频在线观看婷亚洲片国产一区一级在线 | 久久91亚洲精品中文字幕| 18禁超污无遮挡无码免费网站| 亚洲精品国产福利一二区| 国产亚洲漂亮白嫩美女在线 | 色播在线永久免费视频| 亚洲人成网站色在线观看| 最近最好的中文字幕2019免费 | 人人玩人人添人人澡免费| 无码专区—VA亚洲V天堂| 亚洲视频在线免费看| 亚洲免费视频网址| 免费看美女被靠到爽的视频| 亚洲爆乳少妇无码激情| 亚洲人成网站18禁止一区| a在线观看免费视频| 亚洲精品日韩中文字幕久久久| 日本阿v免费费视频完整版| 亚洲丶国产丶欧美一区二区三区| 午夜国产大片免费观看| 久久99精品免费一区二区| 亚洲天天做日日做天天欢毛片| 国产成人免费网站| 黄色a三级三级三级免费看| 亚洲国产精品无码久久SM| 免费福利视频导航| 男性gay黄免费网站| 国产亚洲综合一区柠檬导航| 国产免费的野战视频| 风间由美在线亚洲一区| 精品亚洲永久免费精品| 无人在线观看免费高清视频| 一个人看的www免费高清| 亚洲视频欧洲视频| www亚洲精品少妇裸乳一区二区| 日本免费人成网ww555在线|