设计原则:约定的界面(conventional interfaces)。
范例:“流结构”化的 sum-odd-squares 和 even-fibs
1 (define (filter predicate sequence) 2 (cond ((null? sequence) '()) 3 ((predicate (car sequence)) 4 (cons (car sequence) 5 (filter predicate (cdr sequence)))) 6 (else (filter predicate (cdr sequence))))) 7 8 (define (accumulate op initial sequence) 9 (if (null? sequence) 10 initial 11 (op (car sequence) 12 (accumulate op initial (cdr sequence))))) 13 14 (define (enumerate-interval low high) 15 (if (> low high) 16 '() 17 (cons low (enumerate-interval (+ low 1) high)))) 18 19 (define (enumerate-tree tree) 20 (cond ((null? tree) '()) 21 ((not (pair? tree)) (list tree)) 22 (else (append (enumerate-tree (car tree)) 23 (enumerate-tree (cdr tree)))))) 24 25 (define (sum-odd-squares tree) 26 (accumulate + 27 0 28 (map square 29 (filter odd? 30 (enumerate-tree tree))))) 31 (define (even-fibs n) 32 (accumulate cons 33 '() 34 (filter even? 35 (map fib 36 (enumerate-interval 0 n)))))
在描述一种语言时,应该将注意力集中到语言的基本原语,它的组合手段以及它的抽象手段,这是最重要的。
(We emphasized the importance of describing a language by focusing on the language's primitives, its means of combination, and its means of abstraction.)
部分习题:
exercise 2.33
1 (define (map p sequence) 2 (accumulate (lambda (x y) 3 (cons (p x) 4 y)) 5 '() 6 sequence)) 7 8 (define (append seq1 seq2) 9 (accumulate cons seq2 seq1)) 10 11 (define (length sequence) 12 (accumulate (lambda (x y) 13 (+ 1 y)) 14 0 15 sequence))
exercise 2.34
1 (define (horner-eval x coefficient-sequence) 2 (accumulate (lambda (this-coeff higher-terms) 3 (+ this-coeff 4 (* x higher-terms))) 5 0 6 coefficient-sequence))
exercise 2.35
1 (define (map-tree p sequence) 2 (map (lambda (sub-seq) 3 (if (pair? sub-seq) 4 (map-tree p sub-seq) 5 (p sub-seq))) 6 sequence)) 7 8 (define (count-leaves tree) 9 (accumulate (lambda (x y) 10 (if (pair? x) 11 (+ (count-leaves x) y) 12 (+ x y))) 13 0 14 (map-tree (lambda (x) 1) tree)))
exercise 2.36
1 (define (accumulate-n op init seqs) 2 (if (null? (car seqs)) 3 '() 4 (cons (accumulate op init (map car seqs)) 5 (accumulate-n op init (map cdr seqs)))))
exercise 2.38
exercise 2.39
1 (define (reverse-right sequence) 2 (fold-right (lambda (x y) 3 (append y (list x))) 4 '() 5 sequence)) 6 7 (define (reverse-left sequence) 8 (fold-left (lambda (x y) 9 (cons y x)) 10 '() 11 sequence))
exercise 2.40
1 (define (unique-pairs n) 2 (flatmap (lambda (i) 3 (map (lambda (j) (list i j)) 4 (enumerate-interval 1 (- i 1)))) 5 (enumerate-interval 1 n)))
exercise 2.41
1 (define (tri-pairs n) 2 (let ((range (enumerate-interval 1 n))) 3 (flatmap (lambda (i) 4 (flatmap (lambda (j) 5 (map (lambda (k) (list i j k)) 6 range)) 7 range)) 8 range))) 9 (define (tri-sum-s s n) 10 (filter (lambda (x) 11 (= (accumulate + 0 x) s)) 12 (tri-pairs n)))