3

在我上的一堂课中,我们使用旧的 R5RS 标准方案来解决 SICP 作业。我喜欢先测试开发,所以我认为单元测试框架会很好,我选择了 SchemeUnit 来编写小测试。

到目前为止,这工作得很好,只是在输出中测试原语(字符串、数字等),但是在尝试测试列表时遇到了障碍。这可能与用于运行测试的 Scheme 方言的差异有关:

foo.scm: (define a-list (list 2))

foo-tests.scm: (check-equal? a-list (list 2))

运行测试时的结果:

Unnamed test 
FAILURE
name:       check-equal?
location:   tester.scm:22:3
actual:     {2}

expected:   (2)

为了使测试套件运行,我必须添加"#lang scheme/base 到 foo-tests.scm 和requireschemeunit 包的顶部。在 foo.scm 中,我需要在顶部拥有#lang r5rs和。(#%provide (all-defined))

我猜列表在 R5RS 和“方案/基础”中的实现方式有所不同。有什么办法让他们一起工作吗?为什么会失败({} vs ())?

4

1 回答 1

4

是的,正如您所注意到的,列表在#lang r5rsvs中的实现方式不同#lang scheme/base。如果可以在您foo-tests.scm的 r5rs 中编写测试,那将有助于消除可能的混淆。

您应该可以通过将其放在文件顶部来执行此foo-tests.scm操作。

#lang r5rs

(#%require schemeunit)
(#%require "foo.scm")

;; Now you can add your tests here:
(check-equal? a-list (list 1 2 3))

如果测试套件是用相同的语言编写的,那么结构——尤其是列表的表示——应该匹配。上面的测试应该有望通过。

r5rs详细说明列表与#lang scheme(and ) 中的列表之间的区别#lang racket:Racket 使用不可变的 cons 对来表示列表。不可变的 cons 对不支持 r5rs 的set-car!andset-cdr!函数,因此#lang r5rs使用内置的不可变对将不忠实于该语言的标准。为了支持 r5rs 标准,Racket 包含一个单独的可变对数据类型,并在 r5rs 中一致地使用它。但这意味着 Racket 中的标准对和可变对的比较不同。

于 2013-02-17T21:04:00.147 回答