java 与本地编译语言相比,使用虚拟机编译(例如 JVM)有哪些优势?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/3224288/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
What are the advantages of using Virtual Machine compilation (eg. JVM) over natively compiled languages?
提问by barlop
I've heard that the advantage of java is that people can write code, compile it for the JVM, and run it anywhere. Each person just needs a JVM app for their platform.
我听说 java 的优点是人们可以编写代码,为 JVM 编译它,然后在任何地方运行它。每个人只需要一个适用于他们平台的 JVM 应用程序。
Of course, it looks similar to the current situation, where everybody has a compiler specific for their platform. So the advantage isn't explained by that. But I think I see the explanation.. the issue must be that in the java situation, you can't or weren't meant to access the real machine directly in an OS specific way.
当然,它看起来类似于当前的情况,每个人都有一个特定于其平台的编译器。所以优势并没有用这个来解释。但我想我看到了解释.. 问题一定是在 java 情况下,您不能或不打算以特定于操作系统的方式直接访问真实机器。
I suppose it'd mean that in other languages, the code itself has to be amended depending on what computer it is running on.
我想这意味着在其他语言中,代码本身必须根据它运行的计算机进行修改。
Can anybody provide short examples of this like a Hello World program that demonstrates this? No doubt it'd be in non-java e.g. C
任何人都可以提供这样的简短示例,例如演示这一点的 Hello World 程序吗?毫无疑问,它会在非 Java 中使用,例如 C
Since it's not something that'd -normally- happen in a Hello World program or most i've seen since the books I used on java, they were unfortunately "how to program" style books, and all the stuff in them didn't demonstrate it(perhaps 'cos they couldn't or didn't want to use java to demonstrate it!). Though they trumpeted it as a big advantage. I'd like to see examples of it.
由于这不是通常发生在 Hello World 程序中的事情,或者自从我在 Java 上使用的书籍以来我见过的大多数事情,不幸的是,它们是“如何编程”风格的书籍,并且其中的所有内容都没有演示它(也许是因为他们不能或不想使用 java 来演示它!)。尽管他们吹嘘这是一个很大的优势。我想看看它的例子。
采纳答案by barlop
I've put together some of the answers..
我整理了一些答案。。
While I haven't tested them.. I see nice examples that make sense to me, from within the answers, of
虽然我还没有测试过它们......但我看到了很好的例子,这些例子对我来说很有意义,从答案中,
Bruno provided an example in C
Bruno 提供了一个 C 语言的例子
#include <win32.h>(An OS specific line and code would have to be rewritten for a different OS)
anything that's limited to using calls in stdio.h and a few others (are portable)
#include <win32.h>(必须为不同的操作系统重写特定于操作系统的行和代码)任何仅限于使用 stdio.h 和其他一些调用的内容(可移植)
Gary, spoke of a case with int. That in C, "an int is 32-bit on a 32-bit box. 64-bits on a 64-bit box" "the portable way is to use int32_t" and a point about C and assembly language.. I have asked around and found that if you go over the limit, it cycles back to 0. So, that'd be a case of code having a different effect on a different system and compiling, but perhaps not working as intended, and it having to be rewritten.
Gary 谈到了一个带有 int 的案例。在 C 中,“32 位机器上的 int 是 32 位。64 位机器上的 64 位”“可移植的方式是使用 int32_t”以及关于 C 和汇编语言的一点。我问过周围发现如果你超过限制,它会循环回到 0。所以,这就是代码对不同系统和编译产生不同影响的情况,但可能无法按预期工作,它必须是改写。
Thorbj?rn provided a link to examples of assembly language on different CPUs . Win32 ASM for 32-bit CPUs and Win64 for 64-bit. It has a hello world example in each, and says that it's not easy to convert them, since "In Win32, all the parameters are passed via the stack, however in Win64 they are passed via the registers." He said it uses different instructions.. I guess thouh perhaps it's more than that, in the sense that if it's a different assembly language.. and assembly language is an obvious case of non portability.. hence I didn't mention it in the question, but it's good to see the examples at that link. And it's good knowledge to have. Good to see some contemporary assembly languages not obscure machines..
Thorbj?rn 提供了不同 CPU 上汇编语言示例的链接。用于 32 位 CPU 的 Win32 ASM 和用于 64 位 CPU 的 Win64。它在每个示例中都有一个 hello world 示例,并表示转换它们并不容易,因为“在 Win32 中,所有参数都是通过堆栈传递的,而在 Win64 中,它们是通过寄存器传递的。” 他说它使用不同的指令。问题,但很高兴看到该链接上的示例。这是很好的知识。很高兴看到一些当代的汇编语言而不是晦涩的机器。
回答by Jesper
... where everybody has a compiler specific for their platform. So the advantage isn't explained by that.
...每个人都有一个特定于他们平台的编译器。所以优势并没有用这个来解释。
Porting code written in for example C or C++ is almost always muchmore involved than simply recompiling the code. It's certainly not something that an average, non-developer computer user can do easily. Code written in compiled languages is very often written against the API of a specific operating system (the Win32 API, for example) and so it cannot be compiled on other operating systems easily.
移植用例如 C 或 C++ 编写的代码几乎总是比简单地重新编译代码要复杂得多。这当然不是普通的非开发计算机用户可以轻松完成的事情。用编译语言编写的代码通常是针对特定操作系统的 API(例如 Win32 API)编写的,因此无法在其他操作系统上轻松编译。
Java bytecode runs on any platform where there is a Java runtime environment available. The code doesn't need to be recompiled. Ofcourse you can write operating-system specific code in Java, but Java's standard library, and the many free libraries available on the web, provide a very rich cross-platform environment.
Java 字节码可以在任何有 Java 运行时环境的平台上运行。代码不需要重新编译。当然,您可以用 Java 编写特定于操作系统的代码,但是 Java 的标准库以及网络上提供的许多免费库提供了非常丰富的跨平台环境。
Besides portability, running on a virtual machine has other advantages. Java uses a JIT compilerto compile Java bytecode to native machine code at runtime. The JIT compiler can do sophisticated optimizations for the specific CPU that the program is running on and it can use profiling information that wouldn't be available to an ahead-of-time compiler - in principle, a JIT compiler can therefore produce more optimal code than a "normal" compiler.
除了可移植性,在虚拟机上运行还有其他优势。Java 使用JIT 编译器在运行时将 Java 字节码编译为本地机器代码。JIT 编译器可以对运行程序的特定 CPU 进行复杂的优化,并且可以使用提前编译器无法获得的分析信息——原则上,JIT 编译器因此可以生成更优化的代码比“普通”编译器。
Besides the Java VM, there are other virtual machines. For example, Microsoft .NET contains the CLR(Common Language Runtime) and there's also LLVM, which has front-ends for many different languages including C and C++ (and which is supposed to bring the advantages of JIT compilation also to C and C++).
除了 Java VM,还有其他虚拟机。例如,Microsoft .NET 包含CLR(公共语言运行时)和LLVM,它具有许多不同语言的前端,包括 C 和 C++(并且应该将 JIT 编译的优势也带到 C 和 C++) .
回答by gtrak
I think the point is that on java you can do useful things that are portable, too. In C and C++, you sometimes end up having to do pointer arithmetic and worrying what sizes ints are (vary by OS and CPU) and such. There are fixes in the standards for dealing with that in a portable way, but java has been designed with this in mind from the start. There is another benefit of the JVM, I think. Things like jython and scala are able to use the vast java libraries (and any other available java class) as if they were part of their own language. In most other languages, the way to interface with different languages is by using the C ABI, which is somewhat limiting in an OOP world. In this sense, java is the new C. Also, the jvm provides garbage collection and reflection and such nice things.
我认为重点是在 Java 上你也可以做一些可移植的有用的事情。在 C 和 C++ 中,您有时最终不得不进行指针运算并担心 int 的大小(因操作系统和 CPU 而异)等等。以可移植的方式处理该问题的标准中有一些修正,但 Java 从一开始就考虑到了这一点。我认为 JVM 还有另一个好处。jython 和 scala 之类的东西能够使用大量的 Java 库(以及任何其他可用的 Java 类),就好像它们是自己语言的一部分一样。在大多数其他语言中,与不同语言交互的方式是使用 C ABI,这在 OOP 世界中有些限制。从这个意义上说,java 是新的 C。另外,jvm 提供了垃圾收集和反射等好东西。
回答by Bruno
Besides the advantages of the JVM that will allow you to execute code independently of the CPU architecture with reasonable performance thanks to the JIT-compiler, one fundamental advantage of Java is that it's not just a programming language, but a runtime environment with a API common to all the underlying platforms on which it can run (there are some differences occasionally, but they tend to be bugs).
除了 JVM 的优势之外,由于 JIT 编译器,它允许您以合理的性能独立于 CPU 架构执行代码,Java 的一个基本优势是它不仅是一种编程语言,而且是具有通用 API 的运行时环境到它可以运行的所有底层平台(偶尔会有一些差异,但它们往往是错误)。
gcc(GNU Cross Compiler), for example, will let you compile C code for more or less any platform. That's fine in principle for anything that's limited to using calls in stdio.hand a few others. However, you'll run into trouble quite quickly as soon as you try to use something a bit more OS specific, which tends to appears quite quickly: GUI, some I/O, threading, processes, networking.
gcc(GNU 交叉编译器),例如,可以让您为或多或少的任何平台编译 C 代码。原则上,这对于仅限于使用调用stdio.h和其他一些方法的任何事情都没有问题。然而,一旦您尝试使用一些更特定于操作系统的东西,您就会很快遇到麻烦,这些东西往往会很快出现:GUI、一些 I/O、线程、进程、网络。
As soon as you get an #include <win32.h>or similar in your C code, you'll have to rewrite parts of the code to port it to a Linux/OSX platform, some of this work may not be obvious or directly possible.
一旦您#include <win32.h>在 C 代码中获得一个或类似的内容,您就必须重写部分代码以将其移植到 Linux/OSX 平台,其中一些工作可能并不明显或直接可能。
The advantage of Java isn't just its virtual-machine and ability to read and run the same bytecode on any platform, it's also the availability of a rather large library as part of the JRE (for example J2SE) and a common threading and networking model.
Java 的优势不仅在于它的虚拟机以及在任何平台上读取和运行相同字节码的能力,还在于作为 JRE(例如 J2SE)的一部分的相当大的库的可用性以及公共线程和网络模型。
回答by Thorbj?rn Ravn Andersen
Of course, it looks similar to the current situation, where everybody has a compiler specific for their platform.
当然,它看起来类似于当前的情况,每个人都有一个特定于其平台的编译器。
The thing you need to understand is that even if there is a compiler specific for each platform, the languages are slightly different (unless it is the exact same compiler, which is rare for others than the gcc compiler), and that the platform the programs see are vastly different. "Oh, we have 64-bit integers here, and you need to use X11 to do graphics etc etc etc". You need to handle these things in code, and just the fact that there exist a pretty big GNU project just for handling the configuration of specifying these differences to programs (automake) should indicate that this is not a trivial matter.
您需要了解的是,即使每个平台都有特定的编译器,语言也略有不同(除非它是完全相同的编译器,这在 gcc 编译器之外的其他编译器中很少见),并且程序的平台看到的差别很大。“哦,我们这里有 64 位整数,你需要使用 X11 来做图形等等等等”。您需要在代码中处理这些事情,并且存在一个相当大的 GNU 项目只是为了处理将这些差异指定给程序(automake)的配置这一事实应该表明这不是一件小事。
The platform provided by a JVM is much more rigidly specified, and your programs behave the sameon all of them. Integers overflowing? Oh, that means do this, and ignore that. etc. This is so well done that it is expectedthat things work the same on all JVM's, and that failures are not due to platform differences between development and deployment machines. You always look first for some external reason and only in the rarest cases you find a bug in the JVM. A very well-engineered piece of work.
JVM 提供的平台指定得更加严格,您的程序在所有平台上的行为都相同。整数溢出?哦,这意味着做这个,而忽略那个。等等。这做得非常好,预计所有 JVM 上的事情都一样,并且失败不是由于开发和部署机器之间的平台差异。您总是首先寻找一些外部原因,只有在极少数情况下才会发现 JVM 中的错误。一部精心设计的作品。
回答by Daniel C. Sobral
The main advantage, to me, is the library portability. Libraries might have version dependencies between themselves, but, other than that, a JAR just works.
对我来说,主要优点是库的可移植性。库之间可能有版本依赖关系,但除此之外,JAR 可以正常工作。
There isthe so-called classloader hell, but that's not nearly as common.
还有就是所谓的类加载器地狱,但几乎不一样普遍。
In most other languages, you either have to find the correct library binary, or you have to download the sources to install it.
在大多数其他语言中,您要么必须找到正确的库二进制文件,要么必须下载源代码进行安装。
回答by Fanatic23
Guess you are talking of porting issues. Indeed JVM is what is spoken of in popular literature, that Java eliminates the need for code porting is a shade more subtle.
猜你说的是移植问题。事实上,JVM 就是流行文献中所说的,Java 消除了代码移植的需要,这有点微妙。
You don't have to look too far. A small industry of Windows to UNIX code porting developers [and vice versa] exist for this precise reason. Want examples? How about things like those near, far pointers in C? Or using __declspec(dllexport) to create a Windows specific dll while gcc will have none of this and you need -shared option?
你不必看得太远。正是出于这个原因,存在一个小型的 Windows 到 UNIX 代码移植开发人员行业 [反之亦然]。想要例子吗?像 C 中的那些近、远指针之类的东西怎么样?或者使用 __declspec(dllexport) 创建 Windows 特定的 dll 而 gcc 将没有这些并且您需要 -shared 选项?
One of the most difficult scenario was with doing C++ based GUI in particular before QT came into existence. Loads of GUI is still done on .NET, legacy code is on MFC and for Linux/UNIX a lot of legacy code is in XWindows. Java is a godsend in such cases -- most stuff will work without re-inventing the wheel across platforms.
最困难的场景之一是使用基于 C++ 的 GUI,尤其是在 QT 出现之前。大量的 GUI 仍然在 .NET 上完成,遗留代码在 MFC 上,对于 Linux/UNIX,许多遗留代码在 XWindows 中。在这种情况下,Java 是天赐之物——大多数东西都可以在不跨平台重新发明轮子的情况下工作。
回答by joemoe
Portability mostly. The same Java binary can run on Linux/Mac/Windows. Plus SPARC/PPC/x86/x86-64/ARM/MIPS etc. Read: same binary. No recompilation needed. :)
便携性居多。相同的 Java 二进制文件可以在 Linux/Mac/Windows 上运行。加上 SPARC/PPC/x86/x86-64/ARM/MIPS 等。阅读:相同的二进制文件。无需重新编译。:)

