1

每当我尝试使用 drracket r5rs 语言中的foldreduce等 srfi/1 函数时,我会得到一个空列表?错误。经过一些研究,我发现这是由于函数需要和不可变列表但得到一个可变列表的事实。如何在 r5rs 中创建不可变列表,或者这个 srfi/1 设计时没有考虑到 r5rs?

4

2 回答 2

4

这基本上是在重申约翰所说的话,但它确实值得一个完整的答案状态。(约翰,如果您逐字复制此答案,我很乐意删除它...)

Racket 的 R5RS 语言的特点是它非常严格地坚持 R5RS 语言,因此除此之外什么都没有。(也可以为 R5RS 可变对实现 SRFI,但没有人想出适应的代码。)

无论如何,这里的底线是 R5RS 基本上只在那些你想给自己造成只使用基本 r5rs 语言编写的痛苦的极少数情况下有用——这意味着你基本上不能做很多有用的事情. 因此,特别是如果你想感受一下这门语言,你可能会想玩各种超出狭窄 r5rs 世界的东西——为此你应该使用#lang racket.

它在“只是了解语言”方面也更好,您甚至可以将相同的课程应用到其他 Scheme 实现中,记住它们都带有自己的扩展。如果您使用有限的 r5rs 语言,您可能会体验到这种有限语言带来的挫败感,这很容易压倒您可能拥有的任何积极体验。

于 2012-07-06T13:48:55.693 回答
1

由于“球拍”语言使用不可变的 cons 单元,系统附带的 srfi/1 实现也使用不可变的 cons 单元。

由于 R5RS 中的 cons 单元使用可变的 cons 单元,因此您不能将内置 srfi/1 与 DrRacket 中的 R5RS 语言一起使用。

然而,这是一个小问题。下载http://srfi.schemers.org/srfi-1/srfi-1-reference.scm并将其保存在您拥有代码的目录中。

打开它并在第一行插入:

(define (check-arg . more) #t)

然后在您自己的代码中,添加以下行:

(load "srfi-1-reference.scm")

现在 srfi/1 重新定义了地图(以及其他一些)。重新定义的内置操作通常只在意外情况下完成,因此 DrRacket 中的默认设置是抛出错误。因此单击 DrRacket 左下角的 R5RS 语言。选择“选择语言...”。然后单击“显示详细信息”按钮。通过“不允许重新定义初始绑定”删除勾选。

现在运行以下程序:

(load "srfi-1-reference.scm")
(fold + 0 '(1 2 3))

并按预期产生 6。

于 2012-07-04T21:09:50.563 回答