計算機プログラムの構造と解釈 第二版 P40 問題1.38
問題をよむ。
よし、サービス問題的なやつかなと思ったら、大間違いでした。
とりあえず、問題1.38で作ったcont-fracをつかって自然対数の底eを求める問題のようだ。
要はパラメータとして何を入れればいいかって言う部分を考えればいいのかな。
そこでとりあえずグーグルで自然対数の底eについて調べる。
【自然対数の底 e の定義】
自然対数の底 e は以下に示す極限の式で定義されている。
e= lim t→0 ( 1+t ) 1 t
t= 1 s とおくと, t→0 のとき s→0 となる。よって,上式は
e= lim s→∞ ( 1+ 1 s ) sと表すこともできる。
e の値は,2.71828182845904・・・・・・・・・
まー e は 2.7182....ってことで。
問題本文に
eを自然数の底としてe-2の連分数展開がある。
ってことなので、この計算で求められるのは、どうやら、
0.7182...
の部分っぽい
最後に2をたす。。っと
んで、
Niはすべて1
余裕っすね。。。
Diは順に、1, 2, 1, 1, 4, 1, 1, 6, 1, 1, 8,.....
こういうの苦手なんだよね。
何時間考えたでしょうか、キリスト教だったかなんかだと、神は一週間かそこらで世界を作ったようですが、
僕は1週間近くこの問題を考えていたのでした。
ポイントは、iが2, 5, 8, 11っていうと時にDiがちょっと違うので、iの共通なルールを捉えればいい。
そうするとわかるのが、
3で割ると、2余る数ってことかな。
んで、そういうタイミングで何が起きるかというと、
Diが
2, 4, 6, 8
という値に、ううううむ。。。
いったん、さっきの3割ることについて考えてみる。
2 ÷ 3 = 0・・・ 2
5 ÷ 3 = 1・・・ 2
8 ÷ 3 = 2・・・ 2
11 ÷ 3 = 3・・・ 2
いったん、この答えに2を掛けてみると、、
0
2
4
6
で、さっきのDiの時は、、
2
4
6
8
あ、2ずつ足りない。
てことは、
2 * (1 + (i / 3))
って感じ。
ここの上の、(i / 3)は商だけ。
Scheme入門 2. Scheme を電卓代わりに使う
http://www.shido.info/lisp/scheme2.html
商を求めるにはquotient, 余りを求めるには remainder または modulo, 平方根を求めるには sqrt を使います。
ってことで、quotientという関数が使えるようです。
ということで、ソースです。
#!/usr/local/bin/gosh ;; -*- coding: utf-8 -*- ;;回帰的(リカーシブ)プロセスヴァージョン (define (cont-frac-r n d k) (define (cont-frac i) (if (< i k) (/ (n i) (+ (d i) (cont-frac (+ i 1) ))) (/ (n i) (d i)))) (cont-frac 1)) ;;反復的(イテレーシブ)プロセスヴァージョン (define (cont-frac-i n d k) (define (cont-frac i result) (if (= i 0) result (cont-frac (- i 1) (/ (n i) (+ (d i) result))))) (cont-frac (- k 1) (/ (n k) (d k)))) ;; main (define (main args) (display "e=2.71828182845904.... : ") (display (+ 2 (cont-frac-i (lambda (i) 1.0) (lambda (i) (if (= (remainder i 3.0) 2.0) (* 2.0 (+ 1.0 (quotient i 3))) 1.0)) 11) )) (newline)(newline) 0)
んで、結果
e=2.71828182845904.... : 2.7182818352059925
これ、できちゃった系っすね。