我们已经创建了函数定义的各个部分;现在需要将它们组合起来。
首先,while 表达式的内容:
(while (<= 行号 总行数) ; 真或假的测试 (setq 总和 (+ 总和 行号)) (setq 行号 (1+ 行号))) ; 增量器
连同 let 表达式的变量列表,这几乎完成了函数定义的主体。但是,还需要一个微妙的最后要素。
最后的一步是将变量 总和 单独放在 while 表达式之后的一行上。否则,整个函数返回的值将是在 let 主体中最后一个表达式的值,而这是由 while 评估得到的,其值始终为 nil。
这一点乍一看可能不明显。它几乎看起来好像增量表达式是整个函数的最后一个表达式。但是该表达式是 while 主体的一部分;它是以符号 while 开始的列表的最后一个元素。此外,整个 while 循环是 let 主体内的列表。
概述来说,函数将如下所示:
(defun 函数名 (参数列表)
"文档…"
(let (变量列表)
(while (真或假的测试)
while的主体… )
… )) ; 这里需要最后的表达式。
评估 let 的结果将是由 defun 返回的结果,因为 let 不嵌套在任何包含列表中,除了整个 defun。然而,如果 while 是 let 表达式的最后一个元素,函数将始终返回 nil。这不是我们想要的!相反,我们想要的是变量 总和 的值。通过简单地将该符号作为以 let 开始的列表的最后一个元素放置在列表中,它将在之前的元素被评估之后被评估,这意味着在为总和赋予正确值之后才被评估。
通过将以 let 开始的列表打印在一行上,可能更容易看到这一点。这种格式使得显而易见,变量列表 和 while 表达式是以 let 开始的列表的第二和第三个元素,而 总和 是最后一个元素:
(let (变量列表) (while (真或假的测试) while的主体… ) 总和)
将所有内容放在一起,triangle 函数定义如下:
(defun triangle (总行数) ; 带有 ; 增量计数器的版本。 "将三角形中的鹅卵石数量相加。 第一行有一个鹅卵石,第二行有两个鹅卵石, 第三行有三个鹅卵石,依此类推。 参数为总行数。"
(let ((总和 0)
(行号 1))
(while (<= 行号 总行数)
(setq 总和 (+ 总和 行号))
(setq 行号 (1+ 行号)))
总和))
安装 triangle 后,您可以尝试它。以下是两个示例:
(triangle 4) (triangle 7)
前四个数字的总和是10,前七个数字的总和是28。