計算機プログラムの構造と解釈 第二版 P204 問題3.74
問題は二つ
1. 教科書に定義があるsign-change-dector手続きをつくる。
2. 下記の
;(define zero-crossings ; (stream-map sign-change-detector sense-data <expression>))
という問題。
まず、1から
sign-change-dectorは割と簡単。
注意しないといけないのは、2つと引数どっちが今の値か、どっちが前の値か
これは、Alyssaがつくったmake-zero-crossingsを見ればわかる。
2は結構難しくて、ヒントは、
Alyssaがつくったzero-crossing手続きのなかでのmake-zero-crossing手続き。
この手続きの中で、last-valueの初期値を0にしているところだと思った。
ここではsense-dataとしてsinを使いました。
#!/usr/local/bin/gosh ;; -*- coding: utf-8 -*- (load "./modules/stream.scm") (define ones (cons-stream 1 ones)) (define (add-streams s1 s2) (stream-map + s1 s2)) (define integers (cons-stream 1 (add-streams ones integers))) ;;ストリームを見るための便利機能 (define (stream-viewer stream start count) (define (stream-initializer stream init-num) (if (= init-num 0) stream (stream-initializer (stream-cdr stream) (- init-num 1)))) (define (show-stream stream count) (if (= count 0) (print "end") (begin (print (stream-car stream)) (show-stream (stream-cdr stream) (- count 1))))) (begin (print "start") (show-stream (stream-initializer stream start) count))) (define (sign-change-detector new-value old-value) (cond ((and (>= new-value 0) (< old-value 0)) 1) ((and (< new-value 0) (>= old-value 0)) -1) (else 0))) (define sense-data (stream-map (lambda (x) (sin x)) integers)) ;; Alyssa (define (make-zero-crossings input-stream last-value) (cons-stream (sign-change-detector (stream-car input-stream) last-value) (make-zero-crossings (stream-cdr input-stream) (stream-car input-stream)))) (define zero-crossings-alyssa (make-zero-crossings sense-data 0)) ;;単純にストリームから一個前の値がとれれば良い。 ;;だから一個前のストリームはAlyssaの初期値を先頭に加えてやる ;(define zero-crossings ; (stream-map sign-change-detector sense-data <expression>)) (define zero-crossings (stream-map sign-change-detector sense-data (cons-stream 0 sense-data))) ;; main (define (main args) (print "tests for sign-change-detector") (display "(sign-change-detector 2 1): ") (print (sign-change-detector 2 1)) (display "(sign-change-detector -0.1 0.5): ") (print (sign-change-detector -0.1 0.5)) (display "(sign-change-detector -2 -0.1): ") (print (sign-change-detector -2 -0.1)) (display "(sign-change-detector 0.2 -0.5): ") (print (sign-change-detector 0.2 -0.5)) (display "(sign-change-detector 0 0): ") (print (sign-change-detector 0 0)) (display "(sign-change-detector 0 -1): ") (print (sign-change-detector 0 -1)) (display "(sign-change-detector -1 0): ") (print (sign-change-detector -1 0)) (newline) (print "sense-data") (stream-viewer sense-data 0 10) (newline) (print "zero-crossings-alyssa") (stream-viewer zero-crossings-alyssa 0 10) (newline) (print "zero-crossings") (stream-viewer zero-crossings 0 10) (newline) 0)
実行
tests for sign-change-detector (sign-change-detector 2 1): 0 (sign-change-detector -0.1 0.5): -1 (sign-change-detector -2 -0.1): 0 (sign-change-detector 0.2 -0.5): 1 (sign-change-detector 0 0): 0 (sign-change-detector 0 -1): 1 (sign-change-detector -1 0): -1 sense-data start 0.8414709848078965 0.9092974268256817 0.1411200080598672 -0.7568024953079282 -0.9589242746631385 -0.27941549819892586 0.6569865987187891 0.9893582466233818 0.4121184852417566 -0.5440211108893699 end zero-crossings-alyssa start 0 0 0 -1 0 0 1 0 0 -1 end zero-crossings start 0 0 0 -1 0 0 1 0 0 -1 end
できていると思う。