Java Custom class Loader

Source: Internet
Author: User

Objective

Java reflection, the most commonly used Class.forName () method. At completion, the code string is received and the code string is generated by Javacompiler (stored in the bin directory in the Eclipse Project, under Classpath), and then through the Java reflection mechanism, the main method is obtained and executed. The class file name is fixed. When the A.class file is updated, the problem occurs, and the result of the execution of the main method is the same as the result of the first execution.

Program Flow

Code submission, receive code, compile to A.class file->java reflection->main Method execution

Specific code reference: http://www.cnblogs.com/hujunzheng/p/5203067.html

Cause of the problem

  The delegate mechanism of the class loader! Speaking of which, we have to introduce the Java ClassLoader.

Class loaders in Java virtual machines

multiple ClassLoader can be installed in a Java virtual machine, and the system defaults to three main class loaders, each of which is responsible for loading classes at a particular location: BootStrap,extclassloader,appclassloader

The ClassLoader is also a Java class, because the class loader of the Java class is also loaded by the ClassLoader itself, and it is clear that the first ClassLoader is not a Java class, which is BootStrap, written in C + + code, has been encapsulated in the JVM kernel, and Extclassloader and Appclassloader are Java classes.

Property structure diagram for class loader

A picture of theft:

This leads to the conclusion

First my A.class file was updated, then the call to Class.forName () [I want to reload the bytecode file object], then finally loaded by Appclassloader, one of the functions is very important, that is loadclass (), Take a look at the source code for this function, as follows:

protectedClass<?> loadclass (String name,BooleanResolvethrowsclassnotfoundexception{//plus lock, synchronous processing, because it may be multithreaded in the load class synchronized(Getclassloadinglock (name)) {//Check to see if the class has already been loaded, and if it has been loaded, it will not load theClass C =Findloadedclass (name); if(c = =NULL) {           LongT0 =System.nanotime (); Try {               //if the parent of the custom class loader is not NULL, the loadclass of the parent is called to load the class             if(Parent! =NULL) {C= Parent.loadclass (Name,false); } Else {                   //if the parent of the custom ClassLoader is null, call the Findbootstrapclass method to find the class, which is the Bootstrap class loaderc =findbootstrapclassornull (name); }           } Catch(ClassNotFoundException e) {//ClassNotFoundException thrown if class not found//From the Non-null parent class loader         }           if(c = =NULL) {               //If still not found, then invoke Findclass in order//To find the class.              LongT1 =System.nanotime (); //if the parent load class fails, it calls its own Findclass method for class loadingc =Findclass (name); //This is the defining class loader; record the statsSun.misc.PerfCounter.getParentDelegationTime (). Addtime (T1-t0);               Sun.misc.PerfCounter.getFindClassTime (). Addelapsedtimefrom (t1);           Sun.misc.PerfCounter.getFindClasses (). increment (); }       }       if(Resolve) {resolveclass (c); }       returnC; }  }  

If the. class file with the same name is loaded before it is loaded ...

Workaround user-defined class loader

Idea 1: Rewrite loadclass () This function, whether or not loaded. Class Ask price, all reload.

@Override      Public throws classnotfoundexception {        System.out.println (name);         byte [] data = loaderclassdata (name);         return this. DefineClass (name, data, 0, data.length);    };

But it was a mistake, so far it has not been understood ... Main is the class I want to load, the LoadClass () function executes two times, the second time does not know how to call the ...? Who knows, tell me, thanks!

 mainjava.lang.objectjava.io.filenotfoundexception:java\lang\object.  class   (the system cannot find the path specified.) At Java.io.FileInputStream.open (Native Method) at Java.io.FileInputStream.  <init> 53) at Com.ds.tools.MyClassLoader.loadClass (    Myclassloader.java:  78) at Java.lang.ClassLoader.defineClass1 (Native Method) At Java.lang.ClassLoader.defineClassCond (Unknown source) at Java.lang.ClassLoader.defineClass (Unknown source) at JAV A.lang.classloader.defineclass (Unknown Source) at Com.ds.tools.MyClassLoader.loadClass (Myclassloader.java:  79) 

Idea 2: Can only silently rewrite the Findclass () method, the LoadClass () method will call this function, in order to avoid appclassloader check whether the class has been loaded, I put A.class's spawn location in the MyClass directory under the project root directory , In this way Myclassloader delegate appclassloader to A.class load, under the current classpath cannot find the corresponding class, unable to complete the loading of the class (same bootstraploader and Extclassloader will not be found), and ultimately we class loader to complete the loading of classes, the code is as follows:

 Public classMyclassloaderextendsClassLoader {//class loader name    PrivateString Loadername; //the path of the load class    PrivateString Path = ""; Private FinalString FileType = ". Class";  PublicMyclassloader (String loadername) {//to make the system ClassLoader the parent loader for that class loader        Super();  This. Loadername =Loadername; }     PublicMyclassloader (ClassLoader parent, String loadername) {//Displays the parent loader that specifies the class loader        Super(parent);  This. Loadername =Loadername; }     PublicString GetPath () {returnpath; }     Public voidSetPath (String path) { This. Path =path; } @Override PublicString toString () {return  This. Loadername; }    /*** Get a byte array of the. class file *@paramname *@return     */    Private byte[] Loaderclassdata (String name) {InputStream is=NULL; byte[] data =NULL; Bytearrayoutputstream BAOs=NewBytearrayoutputstream (); Name= Name.replace (".", "/"); Try{ is=NewFileInputStream (NewFile (path + name +fileType)); intc = 0;  while( -1! = (c =Is.read ()))            {Baos.write (c); } Data=Baos.tobytearray (); } Catch(Exception e) {e.printstacktrace (); } finally{            Try {                if(Is! =NULL) Is.close (); if(BAOs! =NULL) Baos.close (); } Catch(IOException e) {e.printstacktrace (); }        }        returndata; }        /*** Get Class object*/@Override PublicClass<?> Findclass (String name)throwsclassnotfoundexception{byte[] data =loaderclassdata (name); return  This. defineclass (name, data, 0, data.length); }     Public Static voidMain (string[] args)throwsclassnotfoundexception, Instantiationexception, Illegalaccessexception, SecurityException, Nosuchmethodexception, IllegalArgumentException, invocationtargetexception { for(inti=0; i<5; i++) {Myclassloader loader1=NewMyclassloader ("Myclassloader"); //String Path = new File (Myclassloader.getsystemclassloader (). GetResource (""). GetPath ()). GetParent ();Loader1.setpath ("myclass/"); Class<?> clazz = Loader1.loadclass ("Main");        System.out.println (Clazz.getname ()); }    }}

Java Custom class Loader

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.