Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/346.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
为什么';java有没有非字节码编译器?_Java_Compilation_Jvm_Bytecode - Fatal编程技术网

为什么';java有没有非字节码编译器?

为什么';java有没有非字节码编译器?,java,compilation,jvm,bytecode,Java,Compilation,Jvm,Bytecode,可能重复: 我知道Java是字节码编译的,但当使用JIT时,它会将“热点”编译为本机代码。为什么没有一个程序将程序编译成本地代码?< /p> 有一个选项,可以编译二进制源代码中的java源代码文件,它被称为“自由软件基金会”。 Sun/Oracle没有正式支持它,但我使用了编译器,它做得很好;) 因为编译字节码就足够了。 如果您要编译自己的代码,那么您还必须编译所有库。 从两个角度来看,这是一个真正的问题: 1.许可-大多数代码不会更改 2.您已经“重新编译”了数以百万吨计的代码:-)它应该编

可能重复:


我知道Java是字节码编译的,但当使用JIT时,它会将“热点”编译为本机代码。为什么没有一个程序将程序编译成本地代码?< /p> 有一个选项,可以编译二进制源代码中的java源代码文件,它被称为“自由软件基金会”。
Sun/Oracle没有正式支持它,但我使用了编译器,它做得很好;)

因为编译字节码就足够了。 如果您要编译自己的代码,那么您还必须编译所有库。 从两个角度来看,这是一个真正的问题: 1.许可-大多数代码不会更改
2.您已经“重新编译”了数以百万吨计的代码:-)

它应该编译到哪个平台本机代码?
Windows、Mac、Linux?
如果开发人员在不同的平台上工作,而应用程序将在不同的平台上运行,该怎么办? 如果服务器机房或桌面上的应用程序平台发生变化,该怎么办


我看不出有什么好处,现在的JVM似乎足够快,可以满足非常广泛的需求。

Java作为一种语言,可以像任何语言一样以多种方式实现。这包括完整解释、字节码编译和本机编译。看

VM规范定义了字节码应该如何加载和执行。它定义了编译的类格式和执行语义,例如线程问题,以及所谓的“内存模型”。看

虽然最初的意思是结合在一起,但语言和虚拟机是不同的规范。您可以将另一种语言编译成Java字节码,并在JVM上运行它。您可以用不同的方式实现Java语言,尤其是在没有VM的情况下,只要遵循预期的语义即可


当然,两者仍然是相关的,如果没有字节码解释,Java的某些方面可能很难得到支持,例如返回字节码的自定义
ClassLoader
(请参阅)。我猜字节码需要立即JIT到本机代码中,或者根本不受支持

有几种产品可以将java程序编译成本机代码,但是它们并不完美,而且根本不像JIT编译器。一些差异包括:

  • “编写一次,到处运行”-它只在编译它的目标上工作
  • 动态代码—您不能在运行时加载JAR或其他Java代码,这通常是应用程序服务器、GUI构建器等的一项功能
  • 运行时评测—很多JIT编译器操作都涉及到理解代码在运行时正在做什么,而不是它在静态分析下可能做什么,这意味着JIT可以在正确的情况下胜过本机编译的应用程序
  • 无法支持所有Java功能。像反射这样的事情在编译程序中不会有什么意义
  • 占用空间大—当它被编译为本机代码时,JVM提供给您的所有库都必须绑定到包中,从而导致占用空间非常大。弄清楚什么可以省略是一个棘手的问题

  • 因此,对于应用程序的某个子集来说,编译为本机代码是可能的,但随着虚拟机的速度越来越快,上述第5个问题并没有得到真正的改进(尽管项目应该对此有所帮助),对于现实世界的应用程序来说,这不是一个非常有吸引力的选择。

    这是Sun做出的不允许这样做的决定,因为他们想将Java定位为固有的多平台。因此,他们希望确保编译的任何Java应用程序都能在任何具有JVM的平台上运行。这就防止了Java二进制文件在线可用,而这些文件不会在某些硬件或操作系统上运行。

    因为这样它就不再是Java程序了。这将是一个本机应用程序,恰好在后台使用Java库。GCJ编译器可以将Java源代码编译为本机代码:@MarcB,我真的没有收到你的评论。你是说它不再是字节码了?(字节码程序与其说是Java程序,不如说是汇编程序,不如说是C++程序。)字节码的全部意义在于它是可移植的。您可以在任何有JVM的地方使用该字节码并运行它。一旦编译为本机,它就不再是字节码——它是x86/mips/arm/任何汇编程序,并且不再是可移植的。因为Java的全部前提是可移植性,一旦你删除它,它基本上就不再是Java了。@MarcB:Bytecode,或可移植性,是一个实现细节。如果编译器接受符合JSP的任何程序并输出一个程序(无论是用JVM的机器代码编写的,还是用实际运行物理计算机的CPU的机器代码编写的),那么它就是Java语言的编译器。当然,您可能会失去与流行JVM的互操作性,并失去其他实现的一个重要属性,但Java语言并不是由其实现或可移植性定义的。如果我没有说错的话,GCJ是一个死项目。另外,本机代码的性能也不好。请看我这里的问题:还有一个商业实现叫做JET:不过我有时会使用GCJ,它不太坏。不,您不必重新编译成吨的代码。只需重新编译已更改的代码。当然,它们必须再次链接。重新编译成吨的代码是一种速记——这意味着如果您想将代码编译为本机代码,可能您想在本机处理器上运行应用程序——而不使用jvm。如果是真的,则必须在jvm、默认库和其他库中编译。(如果要编译nod,您如何知道哪个类将被排除在外。如果您留下了一个类,您必须确保在必要时加载它们的方式