; stream processing for Dr. Scheme (define the-empty-stream '()) (define empty-stream? null?) (define head car) ; tails are promises (define (tail stream) (force (cdr stream))) ; ANSI/IEEE standard? ; converts (cons-stream exp1 exp2) ; into (cons exp1 (delay exp2)) (define (cons-stream-expander exp1 exp2) `(cons ,exp1 (delay ,exp2))) ; define-syntax? ; cons-stream macro expander (define-macro cons-stream cons-stream-expander) ; best I can do: (define (stream? val) (or (empty-stream? val) (and (pair? val) (promise? (cdr val))))) ;======================================= ; some stream utilities (define (natural? n) (and (integer? n) (<= 0 n))) ; selecting items from a stream: (define (stream-ref stream n) (do ((count n (- count 1)) (members stream (tail members))) ((or (zero? count) (empty-stream? members)) (if (empty-stream? members) (error "out of range" stream-ref n) (head members))))) ; streams from lists (define (list->stream vals) (if (null? vals) the-empty-stream (cons-stream (car vals) (list->stream (cdr vals))))) (define (stream->list stream) (if (empty-stream? stream) '() (cons (head stream) (stream->list (tail stream))))) ; tests (define vowels (list->stream '(a e i o u))) (define digits (list->stream '(0 1 2 3 4 5 6 7 8 9))) ;Streams as Signals (define (stream-map amp msgs) (if (empty-stream? msgs) the-empty-stream (cons-stream (amp (head msgs)) (stream-map amp (tail msgs))))) (define (stream-filter noise? msgs) (cond ((empty-stream? msgs) the-empty-stream) ((noise? (head msgs)) (stream-filter noise? (tail msgs))) (else (cons-stream (head msgs) (stream-filter noise? (tail msgs)))))) ; tests (define (square x) (* x x)) (define even-digits (stream-filter even? digits)) (define square-digits (stream-map square digits)) ;Infinitely Long Streams (define (m-to-n m n) (if (> m n) the-empty-stream (cons-stream m (m-to-n (+ m 1) n)))) (define (from-m m) (cons-stream m (from-m (+ m 1)))) (define nats (from-m 0))