1.1

1.1.1

カッコでかこわれたのをcombinationっていう

(hoge fuga piyo moge muri)

1.1.2

オブジェクトの名前付けにもdefineを使う.defineはcombinationではなく,special formという

(define size 2)

名前とオブジェクトの対応はenvironmentにより記憶される(正確にはglobal environment)

1.1.5 手続き適用のためのSubstitution Model(置き換えモデル?)

置き換えモデルはあくまでインタプリタの動作理解のために導入したもので,実際3章でよりまともなモデルで置き換えられる
置き換え方法には

  • normal-order evaluation: 一番浅い式から解決?
  • applicative-order evaluation: 一番深い式から解決?

があり一長一短.Lispではapplicative-orderを採用

1.1.6 条件式と述部

cond.switchのようなもの.special form

(cond (<p1> <e1>)
      (<p2> <e2>)
      (<pn> <en>))

( )をclauseという.if文もあるよ

序盤は

かったるい?飛ばしていい?でもところどころ大事なことに触れてるから(environmentとか),読み返さんようにまじめによもう

1.1.7

演習1.6なるほどなー

演習解答

;;; 1.1 ;;;
;;;実行するだけ.小指怪我したので省略

;;; 1.2
(/ (+ 5 4 (- 2 (- 3 (+ 6 (/ 1 3)))))
   (* 3 (- 6 2) (- 2 7)))

;;; 1.3 ;;;
(define (sum-sq x y)
  (+ (* x x) (* y y)))

(define (sq-larger x y z)
  (cond ((and (< x y) (< x z)) (sum-sq y z))
	((and (< y z) (< y x)) (sum-sq z x))
	(else (sum-sq x y))))

;;; 1.4 ;;;
;bが0より大きいかどうかで演算子変わってるね.おもしろー

;;; 1.5 ;;;
(define (p) (p))
(define (test x y)
  (if (= x 0)
      0
      y))
; のとき,下の式がapplicative-orderと normal-orderでどう評価されるか 
(test 0 (p))

;; applicative-order
(test 0 (p))
(test 0 (p))
; 無限ループ

;; normal-order
(if (= 0 0) 0 p)
; で 0返って終了

;;; 1.6 ;;;
;; if文をこう書いて
(define (new-if predicate then-clause else-clause)
  (cond (predicate then-clause)
	(else else-clause)))

;; sqrtのプログラムのifを置き換えた.どうなる?
(define (sqrt-iter guess x)
  (new-if (good-enough? guess x)
	  guess
	  (sqrt-iter (improve guess x)
		     x)))

; if の場合,predicateの結果を見てから then-clause, else-clauseの
; どちらかを評価する.でもnew-ifだと,applicative-orderで評価する
; から,分岐の前に predicate, then-clause, else-clauseすべてを
; 評価しようとする.sqrt-iterの最後の再帰呼び出しで無限ループになる

;;; 1.7 ;;;
; ひどいからなんとかする.小さい数しか対応できてないし
; 根本的に間違ってる
(sqrt       1) ;=> 1.0
(sqrt     0.1) ;=> 0.316245562280389
(sqrt    0.01) ;=> 0.10032578510960605
(sqrt   0.001) ;=> 0.04124542607499115
(sqrt  0.0001) ;=> 0.03230844833048122
(sqrt 0.00001) ;=> 0.03135649010771716

;;; 方針: 平方根を求める値を1近くにするようにフックする
; 100の何乗か求める
(define (_get-figure x figure mag)
  (if (>= x 1.0)
      figure
      (_get-figure (* x mag) (+ 2 figure) mag )))

(define (get-figure x)
  (_get-figure x 0 100.0))

(define (_pow x y result)
  (if (= 0 y)
      result
      (_pow x (- y 1) (* result x))))

(define (pow x y)
  (_pow x y 1.0))

(define (_new-sqrt x figure)
  (/ (sqrt-iter 1.0 (* (pow 100 figure) x)) (pow 10 figure)))

(define (new-sqrt x)
  (_new-sqrt x (get-figure x)))

(new-sqrt       1) ;=> 1.0
(new-sqrt     0.1) ;=> 0.3162278245070105
(new-sqrt    0.01) ;=> 0.10000000000139897
(new-sqrt   0.001) ;=> 0.03162277660203896
(new-sqrt  0.0001) ;=> 0.010000000025490743
(new-sqrt 0.00001) ;=> 0.003162277660168379

;;; 1.8 ;;;
(define (cubert-iter guess x)
  (if (good-enough? guess x)
      guess
      (cubert-iter (improve guess x) x)))

(define (cubert x)
  (cubert-iter 1.0 x))

(define (improve guess x)
  (/ (+ (/ x (* guess guess)) (* 2 guess)) 3))

(define (good-enough? guess x)
  (< (abs (- (* guess guess guess) x)) 0.001))