Title: Streams
1Lecture 16
Streams continue Infinite Streams
2Finite Streams
(define (stream-enumerate-interval low high)
(if (gt low high) the-empty-stream
(cons-stream low (stream-enumerate-i
nterval ( low 1) high))))
(define s (stream-enumerate-interval 1
1000000000))
3Infinite streams
Since streams are delayed, we are not limited to
finite streams!!
Some objects are more naturally infinite
4The integers
(define (integers-from n) (cons-stream n
(integers-from ( n 1))))
(define integers (integers-from 1))
5Integers not divisible by 7
(define (divisible? x y) ( (remainder x y)
0)) (define no-sevens (stream-filter
(lambda (x) (not (divisible? x 7))) integers))
(stream-ref no-sevens 100) ? 117
6Fibonacci sequence
(define (fib-seq-from a b) (cons-stream a
(fib-seq-from b ( a b)))) (define fib-seq
(fib-seq-from 0 1))
7Fibonacci sequence
- (define (fib-seq-from a b)
- (cons-stream a (fib-seq-from b ( a b))))
- (define fib-seq (fib-seq-from 0 1))
- fib-seq
- (0 . ltstructpromisegtfib-seq-from 1 1)
- (stream-ref fib-seq 3)
- (stream-ref (stream-cdr fib-seq) 2)
- (stream-ref (fib-seq-from 1 1) 2)
- (stream-ref (cons 1 (delay (fib-seq-from 1 2)))
2) - (stream-ref (stream-cdr (cons 1 (delay
(fib-seq-from 1 2)) 1) - (stream-ref (fib-seq-from 1 2) 1)
- (stream-ref (cons 1 (delay (fib-seq from 2 3)))
1) - (stream-ref (stream-cdr (cons 1 (delay
(fib-seq-from 2 3)))) 0) - (stream-ref (fib-seq-from 2 3) 0)
- (stream-ref (cons 2 (delay (fib-seq-from 3 5)))
0) - 2
8Finding all the primes using the sieve of
Eratosthenes
9The sieve of Eratosthenes using streams
(define (sieve str) (cons-stream
(stream-car str) (sieve (stream-filter
(lambda (x) (not
(divisible? x (stream-car str))))
(stream-cdr str))))) (define primes (sieve
(stream-cdr integers)))
10The integers, again (implicit version)
We saw the definition (define (integers-from n)
(cons-stream n (integers-from ( n 1)))) (define
integers (integers-from 1))
An alternative definition (define integers
(cons-stream 1 (stream-map (lambda (x) ( x
1)) integers))
input to stream-map
(integers)
1
2
.....
integers
result element 1
.....
1
3
2
11The integers another way
- (define ones (cons-stream 1 ones))
- (define integers
- (cons-stream 1 (add-streams ones integers))
- (define (add-streams s1 s2)
- (stream-map s1 s2))
A direct implementation of add-streams
(define (add-streams s1 s2) (cons-stream (
(stream-car s1) (stream-car s2))
(add-streams (stream-cdr s1) (stream-cdr s2))))
12Implicit definition of the Fibonacci numbers
(define fibs (cons-stream 0
(cons-stream 1 (add-streams
(stream-cdr fibs)
fibs))))
1
1
2
3
13More implicit definitions
(define (scale-stream str factor) (stream-map
(lambda (x) ( x factor)) str) (define double
(cons-stream 1 (scale-stream double 2)))
14The stream of primes another way
(define primes (cons-stream 2
(stream-filter prime? (integers-from
3)))) (define (prime? n) (define (iter ps)
(cond ((gt (square (stream-car ps)) n) t)
((divisible? n (stream-car ps)) f)
(else (iter (stream-cdr ps))))) (iter primes)
- A recursive definition.
- Works because the primes needed to check
primality of the next number are always ready.
15Formulating iterations as stream processes
(define (sqrt x) (define (good-enough? guess)
(lt (abs (- (square guess) x)) 0.001)) (define
(sqrt-improve guess) (average guess (/ x
guess))) (define (sqrt-iter guess) (if
(good-enough? guess) guess
(sqrt-iter (sqrt-improve guess)))) (sqrt-iter
1.0))
16Formulating iterations as stream processes
(contd)
(define (sqrt-stream x) (define (good-enough?
guess) (lt (abs (- (square guess) x)) 0.001))
(define (sqrt-improve guess x) (average
guess (/ x guess))) (define guesses
(cons-stream 1.0 (stream-map
(lambda (guess)
(sqrt-improve guess x))
guesses))) _________________________________
_______________ ______________________________
__________________ ____________________________
____________________)
(stream-car (stream-filter
(lambda(x) (good-enough? x))
guesses)))
17Formulating iterations as stream processes (Cont.)
(define (pi-summands n) (cons-stream (/ 1.0 n)
(stream-map - (pi-summands ( n
2)))))
(pi-summands 1) (1 (stream-map - (pi-summands
3))) (1 (stream-map - (1/3 (stream-map -
(pi-summands 5)))) (1 -1/3 (stream-map -
(stream-map - (pi-summands 5)))) (1 -1/3 1/5
(stream-map - (stream-map - (stream-map -
(pi-summands 7)))))
18Replacing state variables with streams (Cont.)
(define (pi-summands n) (cons-stream (/ 1.0 n)
(stream-map - (pi-summands ( n
2)))))
(define pi-stream (scale-stream (partial-sums
(pi-summands 1)) 4))
(display-stream pi-stream) 4. 2.6666 3.4666 2.895
2 3.3396 2.9760
converges very slowly!
19Speeding up convergence
(define (euler-transform s) (let ((s0
(stream-ref s 0)) (s1 (stream-ref s 1))
(s2 (stream-ref s 2))) (cons-stream
(- s2 (/ (square (- s2 s1))
( s0 ( -2 s1) s2)))
(euler-transform (stream-cdr s)))))
20Speeding Up Convergence (Cont.)
(display-stream (euler-transform
pi-stream)) 3.1666 3.1333 3.1452 3.1396 3.1427 3.
1408
21Speeding up convergence even further
(define (make-tableau transform s) (cons-stream
s (make-tableau transform
(transform s))))
produces a stream of streams s,
(transform s), (transform (transform s)) . . .
S00 S01 S02 S03 S10 S11 S12
S20 S21 S30
22Speeding up convergence even further (Cont.)
(define (accelerated-sequence transform s)
(stream-map stream-car
(make-tableau transform s)))
S00 S01 S02 S03 . . S10 S11 S12 . . .
S20 S21 ,. . . . .
.
(display-stream (accelerated-sequence
euler-transform pi-stream)) 4. 3.1666 3.1421 3.
1415
23Infinite streams of pairs
Want to produce the stream of pairs of all
integers (i,j) with i ? j and bind it to
int-pairs.
Abstraction
Lets solve an even more general problem. Given
two streams S(S1, S2 . . . . .) T(T1, T2 . .
. . .) Consider the infinite rectangular array
(S1,T1) (S1,T2) (S1,T3) . . . (S2,T1)
(S2,T2) (S2,T3) . . . (S3,T1) (S3,T2)
(S3,T3) . . . . . . . . . . . .
24Infinite streams of pairs
(S1,T1) (S1,T2) (S1,T3) . . . (S2,T1) (S2,T2)
(S2,T3) . . . (S3,T1) (S3,T2) (S3,T3) . .
. . . . . . . . . .
Wish to produce all pairs that lie on or above
the diagonal
j
(S1,T1) (S1,T2) (S1,T3) . . .
(S2,T2) (S2,T3) . . .
(S3,T3) . . .
. . .
i
If S and T are both the integers then this would
be int-pairs
25Infinite streams of pairs
(S1,T1) (S1,T2) (S1,T3) . . .
(S2,T2) (S2,T3) . . .
(S3,T3) . . .
. . .
2
1
3
Write a function pairs such that (pairs s t)
would be the desired stream.
Wishful thinking Break the desired stream into
three pieces
26Infinite streams of pairs
(S1,T1) (S1,T2) (S1,T3) . . .
(S2,T2) (S2,T3) . . .
(S3,T3) . . .
. . .
2
1
3
27Infinite streams of pairs
(define (pairs s t) (cons-stream (list
(stream-car s) (stream-car t))
(combine-in-some-way (stream-map (lambda (x)
(list (stream-car s) x))
(stream-cdr t)) (pairs (stream-cdr s)
(stream-cdr t)))))
1
2
3
(define (stream-append s1 s2) (if (stream-null?
s1) s2 (cons-stream (stream-car s1)
(stream-append (stream-cdr s1)
s2))))
28Infinite streams of pairs (contd)
(define int-pairs (pairs integers integers))
29Infinite streams of pairs (contd)
(define (pairs s t) (cons-stream (list
(stream-car s) (stream-car t)) (interleave
(stream-map (lambda (x) (list (stream-car s) x))
(stream-cdr t)) (pairs
(stream-cdr s) (stream-cdr t)))))
(define (interleave s1 s2) (if (stream-null?
s1) s2 (cons-stream (stream-car s1)
(interleave s2 (stream-cdr
s1)))))
30Infinite streams of pairs (contd)
(define (pairs s t) (cons-stream (list
(stream-car s) (stream-car t)) (interleave
(stream-map (lambda (x) (list (stream-car s) x))
(stream-cdr t)) (pairs
(stream-cdr s) (stream-cdr t)))))
- (define int-pairs (pairs integers integers))
- (display-stream int-pairs)
- (1 1) (1 2) (2 2) (1 3) (2 3) (1 4) (3 3) (1 5)
31Isnt there a simpler solution?
(S1,T1) (S1,T2) (S1,T3) . . .
(S2,T2) (S2,T3) . . .
(S3,T3) . . .
. . .
1
2
(define (pairs s t) (interleave (stream-map
(lambda (x) (list (stream-car s) x))
t) (pairs (stream-cdr s) (stream-cdr t)))))
32Would this work?
Infinite loop!!! pairs calls interleave with
pairs as a parameter, which causes pairs to be
evaluated
(S1,T1) (S1,T2) (S1,T3) . . .
(S2,T2) (S2,T3) . . .
(S3,T3) . . .
. . .
1
2
(define (pairs s t) (interleave (stream-map
(lambda (x) (list (stream-car s) x))
t) (pairs (stream-cdr s) (stream-cdr t)))))
(define (interleave s1 s2) (if (stream-null?
s1) s2 (cons-stream (stream-car s1)
(interleave s2 (stream-cdr
s1)))))
Because there is no pre-computed car,
interleave is called againwhich calls pairs and
so on.
33The generalized stream-map(multiple streams)
(define (stream-map proc . argstreams) (if (or
(null? argstreams) (stream-null? (car
argstreams))) the-empty-stream
(cons-stream (apply proc (map stream-car
argstreams)) (apply
stream-map (cons proc (map stream-cdr
argstreams))))))
- Does it work for finite/infinite streams?
- What if some are finite and others infinite?
- What about finite streams with different
lengths?