# 4.1元圆评估者

> 译者： [https://sicp.comp.nus.edu.sg/chapters/73](https://sicp.comp.nus.edu.sg/chapters/73)



我们的JavaScript评估程序将实现为JavaScript程序。 考虑使用本身在JavaScript中实现的评估器评估JavaScript程序似乎似乎是循环的。 但是，评估是一个过程，因此使用JavaScript来描述评估过程是适当的，因为JavaScript毕竟是我们描述过程的工具。 [[1]](73#footnote-1) 以与所评估语言相同的语言编写的评估者被称为_元圆_。

元循环评估器本质上是 [3.2](52) 部分中描述的评估环境模型的JavaScript表示形式。 回想一下，该模型包含三个基本部分：

 <split>1.  若要评估运算符组合，请评估子表达式，然后将运算符应用于子表达式的值。
2.  若要评估函数应用程序组合，请评估函数子表达式和参数子表达式，然后将函数子表达式的值应用于参数子表达式的值。
3.  要将函数应用于一组参数，请在新环境中评估函数的主体。 要构建此环境，请通过框架扩展函数对象的环境部分，在该框架中，函数的形式参数绑定到应用函数的参数。</split> 

这三个规则描述了评估过程的本质，一个基本的循环，其中将要在环境中评估的语句简化为要应用于自变量的函数，然后将其简化为要在新环境中评估的新语句，依此类推。 ，直到我们深入到在环境中查找其值的符号以及直接应用的运算符为止（请参见图 [4.1](74#fig_4.1)[4.1.1节中进行了描述。 HTG10]](74)[4.1](74#fig_4.1) ）。

评估程序的实现将取决于定义要评估的表达式的_语法_的函数。 我们将使用数据抽象使评估程序独立于语言的表示形式。 例如，不是使用一个以符号赋值开头的列表来表示一个赋值，而是使用一个抽象谓词`is_assignment`来测试一个赋值，而使用抽象选择器`assignment_name`和`assignment_right_hand_side` 访问作业的各个部分。 表达式的实现将在 [4.1.2](75)[4.1.3](76) 部分中还介绍了指定功能和环境表示的操作。 例如，`make_function_object`构造复合函数，`lookup_name_value`访问变量的值，`apply_builtin_function`将原始函数应用于给定的参数列表。

* * *

[[1]](73#footnote-link-1) Even so, there will remain important aspects of the evaluation process that are not elucidated by our evaluator. The most important of these are the detailed mechanisms by which functions call other functions and return values to their callers. We will address these issues in chapter 5, where we take a closer look at the evaluation process by implementing the evaluator as a simple register machine.

[[2]](73#footnote-link-2) If we grant ourselves the ability to apply primitives, then what remains for us to implement in the evaluator? The job of the evaluator is not to specify the primitives of the language, but rather to provide the connective tissue—the means of combination and the means of abstraction—that binds a collection of primitives to form a language. Specifically:

*   评估器使我们能够处理嵌套表达式。 例如，尽管简单地应用基元就足以评估语句`1 + 6;`，但不足以处理`1 + (2 * 3);`。 就原始函数`+`而言，其参数必须是数字，如果将表达式`2 * 3`作为参数传递给它，它将使它感到窒息。 评估程序的重要作用之一是编排功能，以使`2 * 3`在作为`+`的参数传递之前减少到6。
*   评估者允许我们使用变量。 例如，用于加法的原始函数无法处理诸如`x + 1`之类的表达式。 我们需要一个评估器来跟踪变量并在调用原始函数之前获取其值。
*   评估者使我们能够定义复合函数。 这包括跟踪函数定义，了解如何在评估表达式时使用这些定义以及提供一种使函数能够接受参数的机制。
*   评估程序提供语言的其他构造，例如顺序构成和条件表达式。

 