`
beyondqinghua
  • 浏览: 42016 次
  • 性别: Icon_minigender_1
  • 来自: 南昌
社区版块
存档分类
最新评论

认识java的类加载器(二)

    博客分类:
  • JSE
阅读更多

2、如何实现自定义的编译器

通常,一个编译器不仅仅要求编译您当前要编译的类,它必须先编译它说依赖的其他类,等其依赖的类加载进来后才能编译当前类,即其必须逐个编译它所依赖的每一个类。而且加载前必须把原代码文件与存在的编译文件的修改时间比较,如果原代码的修改时间后于编译过的文件,那么必须重新编译原文件。

import java.io.*;

 

//自定义类加载编译器

public class Compilation extends ClassLoader{

   

    //加载类的二进制代码

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

       

        //读取类文件

        File file = new File(fileName);

        if(!file.exists()){

            return null;

        }

        FileInputStream input = new FileInputStream(file);

        long length = file.length();

        byte[] bt = new byte[(int)length];

       

        int rl = input.read(bt);

       

        if(rl != length){

            throw new IOException("不能读取所有内容");

        }

        input.close();

       

        return bt;

    }

   

    //编译原代码文件

    private boolean compile( String javaFile ) throws IOException {

    // 知会用户在编译的文件

    System.out.println( "编译类 : "+javaFile );

 

    // 启动java编译器

    Process p = Runtime.getRuntime().exec( "javac "+javaFile );

 

    // 等待编译完成

    try {

      p.waitFor();

    } catch( InterruptedException e ) {

         System.out.println("编译失败");

    }

 

    // 返回子进程的出口值,值 0 表示正常终止。

    int ret = p.exitValue();

   

    return ret==0;

  }

 

  public Class loadClass( String name, boolean resolve )

      throws ClassNotFoundException {

       

    System.out.println("加载类: "+ name);

    //目标class对象

    Class clas = null;

    // 查看是否已经加载该类

    clas = findLoadedClass( name );

   

    //把类的包结构转化成系统文件目录

    String fileStub = name.replace( '.', '/' );

   

    String javaFilename = fileStub+".java";

    String classFilename = fileStub+".class";

    File javaFile = new File( javaFilename );

    File classFile = new File( classFilename );

 

    // 查看是否是最新编译的文件

    if (javaFile.exists() &&

         (!classFile.exists() ||

          javaFile.lastModified() > classFile.lastModified())) {

      try {

        // 编译文件

        if (!compile( javaFilename ) || !classFile.exists()) {

          throw new ClassNotFoundException( "没找到类文件: "+javaFilename );

        }

      } catch( IOException ie ) {

        throw new ClassNotFoundException( "找不到类 : " + name);

      }

    }   

   

    if(classFile.exists()){

         //获取字节码

         try {

           byte raw[] = loadClassData(classFilename);

           // 转化成class对象

           clas = defineClass( name, raw, 0, raw.length );

         } catch( IOException e){

             System.out.println("转化成class对象失败:" + classFilename);

         }

    }

   

    // 查找classpath中是否存在

    if (clas == null) {

      clas = findSystemClass(name);

    }

    // 是否需要分析字节码

    if (resolve && clas != null)

      resolveClass( clas );

    // 找不到该类

    if (clas == null)

      throw new ClassNotFoundException( "类不存在" );

    return clas;

  }

}

public class Pig{

    public Pig(){

            new PigSon();

    }

}

public class PigSon{

    public PigSon(){

        try{

            Class.forName("PigSon2");

        }catch(Exception e){

            System.out.println(e.getMessage());

        }

        System.out.println("This is PigSon");

    }

}

public class PigSon2{

    public PigSon2(){

        System.out.println("This is PigSon2");

    }

}

public class TestCompilation{

    public static void main(String[] args){

        Compilation cp = new Compilation();

        try{

            cp.loadClass("Pig",true).newInstance();

        }catch(Exception e){

            System.out.println(e.getMessage());

        }

    }

}

注意运行时不要编译Pig,PigSon,PigSon2,这样才能够调用自定义的编译器。

加载类: Pig

编译类 : Pig.java

加载类: java.lang.Object

加载类: java.lang.Throwable

加载类: java.lang.Exception

加载类: PigSon

加载类: java.lang.Class

加载类: PigSon2

编译类 : PigSon2.java

加载类: java.lang.System

加载类: java.io.PrintStream

This is PigSon

This is a pig

分享到:
评论

相关推荐

    深入探讨 Java 类加载器

    【深入探讨 Java 类加载器】 Java 类加载器是Java虚拟机(JVM)的核心组成部分,它的主要任务是将Java类的字节码加载到JVM中以便执行...无论是解决运行时问题还是设计复杂的系统架构,都需要对类加载器有深刻的认识。

    Java类加载原理浅析

    **自定义类加载器**是Java提供的强大特性,允许开发者创建自己的类加载器,实现特定的加载逻辑。例如,你可以实现热部署,动态加载网络上的类,或者对类进行加密解密后再加载等。 除了基础的类加载,还有**类的全...

    认识Java的Class类.doc

    默认的类加载器是bootstrap loader,当字段为null时,表示类是由引导类加载器加载的。 5. **forName方法**:`Class.forName()`是Class类的一个静态方法,可以根据类名动态加载类并返回对应的Class对象。有两个版本...

    JVM实战-JVM类加载机制案例分析

    通过实践操作,掌握类的加载、连接与初始化过程,了解不同类型的类加载器及其工作原理,学会创建自定义的类加载器,并对类的卸载有所认识。实验将结合具体的Java程序实例,运用单例模式对静态变量和对象进行初始化,...

    java基础讲义-帮助大家简单认识JAVA

    字节码加载器负责加载代码,字节码校验器则检查代码是否符合安全规范,防止恶意代码的执行。Java还提供了多线程支持,通过Thread类可以轻松创建和管理多个并发执行的线程,实现程序的并行性和实时交互。 Java的可...

    《 从NoSuchMethodError看jvm编译和class加载方式》的测试项目代码

    JVM(Java虚拟机)采用“双亲委派模型”加载类,即当一个类被加载时,它会首先尝试由启动类加载器(Bootstrap ClassLoader)加载,如果该类不在启动类加载器的路径中,则会委托给扩展类加载器(Extension ...

    《JAVA语言程序设计》期末考试试题及答案_java期末考试_java_

    1. **Java基础知识**:包括Java的历史、特点、运行机制(JVM)、类加载器以及Java与其他编程语言的对比。这部分会考察对Java的基本认识和理解。 2. **语法基础**:涉及变量、数据类型、运算符、流程控制(如if语句...

    Java做的幻灯片

    总结来说,这个“Java做的幻灯片”项目展示了Java在多媒体应用中的能力,通过`MediaTracker`确保图片加载的可靠性,利用双缓冲技术提供流畅的视觉体验,这些都是Java GUI编程中的重要概念和技术。同时,它也提醒我们...

    Java对象的创建过程结合反射

    因此,使用反射创建对象时,我们不会看到静态代码块的输出,除非再次使用类加载器加载同一类。 ### 总结 Java对象的创建过程涉及到类的加载、验证、准备、解析和初始化等多个阶段。反射机制为我们提供了一种在运行...

    java学习心得

    当类加载器返回null时,意味着使用了Bootstrap ClassLoader,因为它是由C++实现的,没有对应的Java类加载器。 3. JDK与JRE的区别 JRE(Java Runtime Environment)是运行Java程序所需的环境,包括Java虚拟机(JVM)...

    Java虚拟机规范中文版.pdf

    类加载器在运行Java程序时按需加载类,这允许Java程序进行延迟加载,即仅在需要时才加载类,这有助于优化程序的启动时间和运行时性能。 JVM还提供了执行安全检查的能力,包括数组边界检查和类型检查等,这有助于...

    认识Java(共35张PPT).pptx

    例如,一个简单的Java程序可能包括注释、类定义、变量声明、方法定义以及主方法中的逻辑代码。 在DOS环境下,开发者可以使用简单的命令行指令,如REN(重命名文件),来管理和操作文件。对于初学者,理解这些基础...

    Java雷电游戏,主要用SWING和Java的进程,纯Java代码写的,主要为开发人员对Java线程的认识

    Java雷电游戏是一款基于SWING图形用户界面库和Java进程管理技术开发的纯Java应用程序,旨在帮助开发者加深对Java线程的理解。通过分析这款游戏的源代码,我们可以学习到多个Java编程的重要知识点。 首先,SWING是...

    Java 第1章 了解java含源代码

    - **安全性**:Java具有内置的安全特性,如类加载器和安全管理器,用于防止恶意代码执行。 - **健壮性**:强类型检查、异常处理和严格的数据类型转换有助于创建稳定的程序。 - **可移植性**:Java源代码是独立于...

    JAVA工程师实习一周总结【推荐下载】.doc

    这一周的实习让我对JAVA开发有了更深入的理解,特别是对Java虚拟机(JVM)和类加载器(ClassLoader)机制有了初步的认识。 Java虚拟机是Java语言运行的基础,它负责管理程序的内存空间,包括堆内存、栈内存、方法区...

    大白话带你认识JVM.pdf

    类加载器是JVM的一个关键组件,它的任务是将.java源文件编译成的.class字节码文件加载到JVM中。类加载器分为不同的层次,如引导类加载器、扩展类加载器和应用程序类加载器,它们共同协作完成类的加载工作。加载的类...

Global site tag (gtag.js) - Google Analytics