2

我被HTDP 的练习 17.1.2 的问题困住了。这是我到目前为止所得到的:

(define (cross alist1 alist2)
  (cond
    [(empty? alist1) empty]
    [else (append (list (first alist1)(first alist2))
                  (cons (first alist1)(list (first (rest alist2))))
                  (cross (rest alist1) alist2))]))

(cross '(a b c) '(1 2))
;correctly outputs (list 'a 1 'a 2 'b 1 'b 2 'c 1 'c 2)

这适用于测试用例,但是当第二个列表有超过 2 个元素时,函数就会崩溃。

(cross '(a b c) '(1 2 3))
;outputs (list 'a 1 'a 2 'b 1 'b 2 'c 1 'c 2)

问题似乎是追加后的第二行,因为它只从第二个列表中最多包含两个元素。我应该如何解决这个问题?感谢您的任何见解。:)

4

1 回答 1

2

它仅适用于列表二中的两个元素,因为您仅指定它适用于列表二中的两个元素。我们需要利用抽象的力量。

如果我们使用命令式语言,那么我们会在这个问题上使用嵌套的 for 循环。您从 alist1 的第一个元素开始并匹配 alist2 的所有元素。然后你移动到 alist1 的第二个元素并匹配 alist2 的所有元素。由于我们使用的是函数式语言(Scheme),我们将使用嵌套函数而不是嵌套的 for 循环。

您想编写一个函数,它接受 'a 和 '(1 2 3) 并产生 '(a 1 a 2 a 3),然后另一个函数调用具有不同值 'a 的第一个函数。如果您不希望下面的解决方案为您破坏,您应该忽略的相关代码。

(define (cross alist1 alist2)
 (cond
  ((null? alist1) '())
  (else 
   (append (innercross (car alist1) alist2)
           (cross (cdr alist1) alist2)))))

(define (innercross a1 alist2)
 (cond
  ((null? alist2) '())
  (else
   (cons a1 (cons (car alist2) (innercross a1 (cdr alist2)))))))
于 2010-12-27T05:18:35.797 回答