SICP 読み (151) 4.1.2 式の表現

4.1.3 節の練習問題は一旦スルーで 4.1.4 節までヤッツケた方が良さげな感じ。

問題 4.10 のつづき

4.1.4 まで実装できれば試験できそう。ダウトかどうかは別にして、それまでは試験ができんのでとても気持ちが悪いんです。
とりあえず、問題 4.4 から 4.8 くらいまでのソレが以下。

(define (install-and)
  (define (eval-and exp env)
    (define (eval-and-iter predicates env)
      (let ((ret (eval (car predicates) env)))
	(if (false? ret)
	    false
	    (if (null? (cdr predicates))
		ret
		(eval-and-iter (cdr predicates) env)))))
    (if (null? (cdr exp))
	true
	(eval-and-iter (cdr exp) env)))
  (put 'and 'eval eval-and)
  'done)

(define (install-or)
  (define (eval-or exp env)
    (define (eval-or-iter predicates env)
      (let ((ret (eval (car predicates) env)))
	(if (true? ret)
	    ret
	    (if (null? (cdr predicates))
		false
		(eval-or-iter (cdr predicates) env)))))
    (if (null? (cdr exp))
	false
	(eval-or-iter (cdr exp) env)))
  (put 'or 'eval eval-or)
  'done)

(define (install-let)
  (define (eval-let exp env)
    (eval (let->combination exp) env))
  (define (let->combination exp)
    (if (symbol? (cadr exp))
	(list 'begin
	      (list 'define 
		    (cadr exp)
		    (make-lambda (map car (caddr exp)) (cdddr exp)))
	      (list (cadr exp) (map cadr (caddr exp))))
	(append (list (make-lambda (map car (cadr exp)) (cddr exp)))
		(map cadr (cadr exp)))))
  (put 'let 'eval eval-let)
  'done)

(define (install-let*)
  (define (eval-let* exp env)
    (eval (let*->nested-let exp) env))
 	(eval-or-iter (cdr exp) env)))
  (put 'or 'eval eval-or)
  'done)

本当に動くモノなのかどうか、は動く状態になってみないと分からない。