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))))