资讯专栏INFORMATION COLUMN

Java动态性(1) - 动态编译(DynamicCompile)

MartinDai / 1164人阅读

摘要:动态编译引入了编译机制动态编译的应用场景可以做一个浏览器端编写代码上传服务器编译和运行的在线评测系统服务器动态加载某些类文件进行编译动态编译的两种做法通过调用启动新的进程去操作之前不是真正的动态编译通过动态编译通过动态编译栗子编译成功编译

1.动态编译

Java 6.0 引入了编译机制

动态编译的应用场景:

可以做一个浏览器端编写java代码,上传服务器编译和运行的在线评测系统

服务器动态加载某些类文件进行编译

动态编译的两种做法:

通过Runtime调用javac,启动新的进程去操作(6.0之前,不是真正的动态编译)

Runtime run = Runtime.getRuntime();

Process process = run.exec("javac -cp d:/myjava/Helloworld.java")

通过JavaCompiler动态编译

通过JavaCompiler动态编译

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();

int result = compiler.run(null, null, null, "f:/HelloWorld.java");
Parameters:
in "standard" input; use System.in if null
out "standard" output; use System.out if null
err "standard" error; use System.err if null
arguments arguments to pass to the tool

栗子:

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
int result = compiler.run(null, null, null, "f:/HelloWorld.java");
System.out.println(result==0?"编译成功":"编译失败");
2.动态运行编译好的类

通过Runtime.getRuntime()运行启动新的进程运行

JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
int result = compiler.run(null, null, null, "f:/HelloWorld.java");
System.out.println(result==0?"编译成功":"编译失败");
Runtime run = Runtime.getRuntime();
Process process = run.exec("java -cp f: HelloWorld");
        
BufferedReader w = new BufferedReader(new InputStreamReader(process.getInputStream()));
System.out.println(w.readLine());

通过反射运行编译好的类

import java.io.IOException;
import java.lang.reflect.Method;
import java.net.URL;
import java.net.URLClassLoader;
import javax.tools.JavaCompiler;
import javax.tools.ToolProvider;

public class DynamicCompile {

    public static void main(String[] args) throws IOException {

        JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
        int result = compiler.run(null, null, null, "f:/HelloWorld.java");
        System.out.println(result==0?"编译成功":"编译失败");
    
        try {
            URL[] urls = new URL[]{new URL("file:/"+"f:/")};
            URLClassLoader loader = new URLClassLoader(urls);
            Class c = loader.loadClass("HelloWorld");
            Method m = c.getMethod("main", String[].class);
            m.invoke(null, (Object)new String[]{});//静态方法不用谢调用的对象
            //加Object强制转换的原因
            //由于可变参数是JDK5.0之后才有 m.invoke(null, new String[]{"23","34"});
            //编译器会把它编译成m.invoke(null,"23","34");的格式,会发生参数不匹配的问题
            //带数组的参数都这样做
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/71927.html

相关文章

  • Java动态代理实现原理(模拟实现)

    摘要:很多框架底层都使用了的动态代理技术来实现的,比如大名鼎鼎的这篇文章将带你一步一步揭开动态代理技术的神秘面纱。接下来客户端就可以这样使用了毫秒到目前为止,我们实现的类可以为任何接口生成代理类了,是不是很神奇。 ​ 动态代理是java语言中常用的设计模式,java在1.3版本以后也提供了动态代理技术,允许开发者在运行期间创建接口的代理对象。 很多框架底层都使用了java的动态代理技术...

    K_B_Z 评论0 收藏0
  • 读书笔记之深入理解Java虚拟机

    摘要:前言本文内容基本摘抄自深入理解虚拟机,以供复习之用,没有多少参考价值。此区域是唯一一个在虚拟机规范中没有规定任何情况的区域。堆是所有线程共享的内存区域,在虚拟机启动时创建。虚拟机上把方法区称为永久代。 前言 本文内容基本摘抄自《深入理解Java虚拟机》,以供复习之用,没有多少参考价值。想要更详细了解请参考原书。 第二章 1.运行时数据区域 showImg(https://segment...

    jaysun 评论0 收藏0
  • Java动态编程初探

    摘要:动态编程使用场景通过配置生成代码,减少重复编码,降低维护成本。动态生成字节码操作字节码的工具有,其中有两个比较流行的,一个是,一个是。 作者简介 传恒,一个喜欢摄影和旅游的软件工程师,先后从事饿了么物流蜂鸟自配送和蜂鸟众包的开发,现在转战 Java,目前负责物流策略组分流相关业务的开发。 什么是动态编程 动态编程是相对于静态编程而言的,平时我们讨论比较多的静态编程语言例如Java, 与动态...

    赵连江 评论0 收藏0
  • 【干货】JDK动态代理的实现原理以及如何手写一个JDK动态代理

    摘要:代理模式从类型上来说,可以分为静态代理和动态代理两种类型。然而今天的重点是我们都知道牛逼轰轰的的实现的一种方式是使用的动态代理另一种是,大部分人也会用的动态代理,不过没有研究过的动态代理到底是怎么实现的。 动态代理 代理模式是设计模式中非常重要的一种类型,而设计模式又是编程中非常重要的知识点,特别是在业务系统的重构中,更是有举足轻重的地位。代理模式从类型上来说,可以分为静态代理和动态代...

    forsigner 评论0 收藏0
  • Java代理设计模式(Proxy)的四种具体实现:静态代理和动态代理

    摘要:除了和外,我们还有最后一招我直接把一个代理类的源代码用字符串拼出来,然后基于这个字符串调用的编译期,动态的创建一个新的文件,然后动态编译这个文件,这样也能得到一个新的代理类。 面试问题:Java里的代理设计模式(Proxy Design Pattern)一共有几种实现方式?这个题目很像孔乙己问茴香豆的茴字有哪几种写法? showImg(https://segmentfault.com/...

    gclove 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<