为什么将语法分析与执行分开?

发布于 2025-01-02 08:50:58 字数 312 浏览 1 评论 0原文

在 SICP 第 4 章中,通过将语法分析与执行分离来修改元循环求值器,使 eval 过程看起来像:

(define (eval exp env)
    ((analyze exp) env))

书上说这将节省工作,因为 analyze 将在表达式上调用一次,而执行过程可能会被调用多次。

我的问题是,这种优化是如何进行的?它适用于递归过程调用,但其他情况又如何呢?求值器逐个求值表达式,即使它们具有相同的形式,仍会在每个表达式上调用 eval

In SICP Chapter 4, the metacircular evaluator is modified by separating the syntax analysis from the execution, making the eval procedure look like:

(define (eval exp env)
    ((analyze exp) env))

and the book says that this will save work since analyze will be called once on an expression, while the execution procedure may be called many times.

My question is, how does this optimization work? It will work for recursive procedure calls, but how about other cases? The evaluator evaluates expressions one after another, eval will still be called on each expression even if they have identical forms.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

Spring初心 2025-01-09 08:50:58

您需要看到几件事:(a) analyze 函数对每个表达式精确地遍历一次,(b) analyze 之外没有扫描语法的代码,( c) analyze 返回的函数不会调用自身,因此运行该函数永远不会导致对语法的任何进一步扫描,(d) 这与通常的评估函数不同,在通常的评估函数中,调用函数两次意味着它的语法被扫描两次。

顺便说一句,analyze 的一个更好的名字是 compile ——它确实将输入语言 (sexprs) 翻译成目标语言(一个函数,在这里充当机器代码) )。

You need to see several things: (a) the analyze function walks over each expression exactly once, (b) there is no code outside of analyze that scans the syntax, (c) the function that analyze returns does not call itself therefore running that function never leads to any further scanning of the syntax, (d) this is all unlike the usual evaluation functions where calling a function twice means that its syntax is scanned twice.

BTW, a much better name for analyze is compile -- it really does translate the input language (sexprs) to a target one (a function, acting as the machine code here).

温柔一刀 2025-01-09 08:50:58

编译器和解释器之间的区别在于:

编译器只扫描一次源代码并将其转换为执行代码(可能是机器代码)。下次执行程序时,直接执行执行代码,无需分析源代码,效率很高。

然而,解释器会在您每次执行程序时分析源代码。

这种优化仅在程序被执行多次的情况下才有意义。

正如 @Eli Barzilay 所说,“analyze 的更好名称是 compile< /code>”,你分析的函数就像执行代码。递归函数就像会执行多次的程序。

The difference between a compiler and a interpreter is that:

A compiler scan your source code only once and change it into to execution code (machine code maybe). When you execute your program the next time, you directly execute the execution code without analyzing the source code, which is efficient.

A interpreter, however, analyze the source code each time you execute your program.

This optimization only makes sense in cases of your program will be executed more than once.

As @Eli Barzilay said, "a much better name for analyze is compile", your analyzed functions is like the execution code. The recursive functions are like programs which would be executed more than once.

策马西风 2025-01-09 08:50:58

analyze 只是进行一次语法分析,并将转换后的 definition 等存储在环境中,可以直接通过 lookup-variable-value 使用执行相关程序。

相比之下,原始的元循环求值器扭曲了语法分析和执行,使得每次执行也调用语法分析。

此链接可能有帮助:
http://www.cs.brandeis.edu/ 〜mairson/Courses/cs21b/Handouts/feeley-notes.pdf

analyze just does syntax analyses once and store the transformed definition and so on in the environment which may be used through lookup-variable-value directly when the related procedure is executed.

In contrast, the original metacircular evaluator twists the syntax analysis and execution which makes each execution invokes syntax analysis as well.

This link maybe helpful:
http://www.cs.brandeis.edu/~mairson/Courses/cs21b/Handouts/feeley-notes.pdf

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文