首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >Java解释器或任何解释器到底是如何工作的?

Java解释器或任何解释器到底是如何工作的?
EN

Stack Overflow用户
提问于 2017-05-09 21:10:32
回答 3查看 8.6K关注 0票数 9

我一直在弄清楚一个口译员的确切工作原理,我用谷歌搜索了一下,得出了一些结论,只是希望有人能让我更好地理解口译员的工作。

所以我所理解的是:

java解释器是将代码从高级语言转换成机器format.

  • speaking的软件程序。具体地,关于解释器,它以二进制格式获得代码(其早先由java编译器从源代码翻译成字节码)。现在java解释器的平台是
  1. ,它在其中运行,因此,基本上它将生成可由JVM运行的代码。
  2. ,因此它采用字节码,生成中间代码和目标机器码,并将其提供给JVM。
  3. JVM依次在实现或运行JVM的操作系统平台上执行这些代码。

现在我仍然不清楚在两者之间发生的子过程,即

  1. 解释器生成中间code.
  2. interpreted代码,然后执行optimized.
  3. then目标代码,最后执行。

更多的问题:

  • 所以解释器是单独负责生成目标代码的吗?和执行它?
  • 和执行是否意味着它在JVM或底层操作系统

中执行?

EN

回答 3

Stack Overflow用户

发布于 2017-05-09 21:45:44

给出1000英尺的视角,希望能让事情变得清晰起来:

java应用程序有两个主要步骤:编译运行时。每个进程都有非常不同的功能和目的。下面列出了这两种方法的主要流程:

编译

  • 这(通常)由[com.sun.tools.javac][1]执行,通常在tools.jar文件中,通常在$JAVA_HOME中-与java.jar等位于同一位置。
  • 此处的目标是将.java源文件转换为包含java运行时环境的“配方”的.class文件。

编译步骤:

  1. :读取文件,并剥离其“边界”语法字符,如大括号、分号和圆括号。它们的存在是为了告诉解析器将每个源组件翻译成哪个java对象(在下一篇point).
  2. creation:抽象语法树是如何表示源文件中对此有更多介绍。这是一个文字“树”数据结构,它的根类是[com.sun.tools.JCTree][3]。总体思想是每个表达式和每个语句都有一个java对象。在这个时间点上,人们对每种类型所代表的实际“类型”知之甚少。在创建syntax
  3. Desugar:时,唯一要检查的是字面syntax
  4. Desugar:,这是for循环和其他语法糖被转换为更简单形式的地方。语言仍然是“树”的形式,而不是字节码,所以在编译器变得复杂的地方,这可以很容易地happen
  5. :。Java是一种静态语言,因此编译器必须使用Visitor模式遍历AST,并在tim之前找出所有内容的类型,并确保在运行时所有内容(好吧,几乎)都是合法的,就类型、方法签名等而言。如果某些内容过于模糊或无效,则检查编译fails.
  6. Bytecode:控制流,以确保程序执行逻辑有效(没有不可达的语句等)。如果一切都通过了检查而没有错误,那么AST就会被转换成程序represents.
  7. .class文件写入:的字节码:此时,类文件就被写入了。从本质上讲,字节码是专门机器代码之上的一小层抽象层。这使得移植到其他机器/中央处理器结构/平台成为可能,而不必担心它们之间相对较小的差异。

运行时

  • 每个计算机平台都有不同的运行时环境/虚拟机实施。Java是通用的,但运行时环境是一个完全独立的部分,它只知道如何将字节码从类文件转换成与目标平台兼容的机器码,而且它也针对不同的platform.
  • There进行了高度优化,有许多不同的运行时/ VM实现,但最流行的是Hotspot VM。
  • VM非常复杂,可以在运行时优化您的代码。启动时间很慢,但它在运行过程中基本上会“学习”。
  • 这就是运行中的“JIT”(即时)概念-编译器通过检查正确的类型和语法完成了所有繁重的工作,VM只需在运行过程中将字节码转换并优化为机器码。

还有..。

Java是在JSR 199下标准化的编译器

  • 。虽然不完全属于同一类(找不到确切的JLS),但许多其他语言和工具利用标准化的编译过程/API来使用Oracle提供的高级JVM (运行时)技术,同时允许不同的语法。Java参见ScalaGroovyKotlinJythonJRuby等。所有这些都利用了运行时环境,因为它们转换了不同的语法以与Java编译器
    • 兼容!它相当整洁-任何人都可以用他们想要的任何语法编写高性能语言,因为两者是解耦的。对于JVM

,几乎每一种语言都有相应的调整

票数 7
EN

Stack Overflow用户

发布于 2017-05-10 16:13:26

我将根据我创建DSL的经验来回答。

C是编译的,因为你把源代码传给了gcc,然后在机器代码中运行存储的程序。

Python之所以被解释,是因为您通过将程序源代码传递给解释器来运行程序。解释器读取源文件并执行它。

Java是两者的混合体,因为您将Java文件“编译”为字节码,然后调用JVM来运行它。字节码不是机器码,它需要由JVM解释。Java是介于C和Python之间的一层,因为你不能做像"eval“这样花哨的事情(像在Python中那样在运行时计算代码块或表达式)。然而,Java具有C程序不可能拥有的反射能力。简而言之,Java运行时的设计处于纯编译语言和解释语言之间的中间层,在性能和灵活性方面是这两种语言中最好的(也是最差的)。

然而,Python也有一个虚拟机和它自己的字节码格式。这同样适用于Perl、Lua等。这些解释器首先将源文件转换为字节码,然后解释字节码。

我一直想知道为什么这样做是必要的,直到我为模拟DSL制作了自己的解释器。我的解释器执行词法分析(将源文件拆分为标记),将其转换为抽象语法树,然后通过遍历该树来计算该树的值。出于软件工程的考虑,我使用了一些设计模式,并且我的代码大量使用了多态性。与处理模仿真实计算机体系结构的有效字节码格式相比,这非常慢。如果我创建自己的虚拟机或使用现有的虚拟机,我的模拟将会更快。例如,对于计算一个很长的数值表达式,将其转换为类似于汇编代码的东西会比处理抽象树的分支更快,因为这需要调用大量的多态方法。

票数 2
EN

Stack Overflow用户

发布于 2019-04-29 19:32:47

执行程序有两种方法。

  • By a:在Windows .exe上,它将编程语言(比如.c)中的文本解析为机器码。然后可以独立于编译器执行。

这种编译可以通过将几个.c文件编译成几个目标文件(中间产品),然后将它们链接到单个应用程序或库中来完成。

  • 通过interpreter:解析编程语言(比如.java)中的文本,然后“立即”执行程序。

对于java,这种方法有点混合/堆叠: java编译器javac.java编译成.class文件,然后可能将这些文件压缩到.jar (或.war.ear ...)中。对于抽象堆栈机器,.class文件由更抽象的字节代码组成。

然后,java运行时java (称为JVM、java虚拟机或字节码解释器)可以执行.class/.jar。这实际上是一个java字节码的解释器。

现在,它还在运行时将(部分)字节码转换为机器码。这也称为将字节码转换为机器码的即时编译器。

简而言之:- compiler只是创建代码;- interpreter会立即执行。

解释器将遍历解析的命令/高级中间代码,并用一段代码解释每个命令。间接的,原则上是慢的。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/43870794

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档