Here is a solution to 9.17:
; There are two things that require extra attention in this problem:
; 1. The range of every is ALWAYS a sentence;
; 2. We need the sentence identity constant (which is the empty sentence) so when
; every puts all of its data into a sentence, empty sentences will effectively
; disappear
;
; Here are some examples of identity constants:
; * x + 0 = x (0 is the additive identity)
; * x * 1 = x (1 is the multiplicative identity)
; * (se x '()) --> x (the empty sentence is the sentence identity)
; * (word x "") --> x (the empty word is the word identity)
;
; Keep in mind that if the second input to keep is a word, keep's range is a word;
; if the second input is a sentence, the range is a sentence.
;
; combiner will be the word or sentence function, depending on whether the second
; second input is a word or a sentence.
(define (keep predicate? word-or-sentence)
(let ((combiner (if (word? word-or-sentence) word se)))
(accumulate combiner
(every (lambda (wd) (if (predicate? wd) wd '())) word-or-sentence))))