EoPL reading (131) 3.1 A Simple Interpreter

嫌も応も無く英語が読めんと微妙な世界に突入している模様。

Exercise 3.1

ええと、以下な実装にて
simple-interpreter.scm

(add-load-path ".")
(load "define-datatype")

(define list-of
  (lambda (pred)
    (lambda (val)
      (or (null? val)
          (and (pair? val)
               (pred (car val))
               ((list-of pred) (cdr val)))))))

(define-datatype program program?
  (a-program
   (exp expression?)))

(define-datatype expression expression?
  (lit-exp
   (datum number?))
  (var-exp
   (id symbol?))
  (primapp-exp
   (prim primitive?)
   (rands (list-of expression?))))

(define-datatype primitive primitive?
  (add-prim)
  (subtract-prim)
  (mult-prim)
  (incr-prim)
  (decr-prim))

program-to-list.scm

(add-load-path ".")
(load "simple-interpreter")

(define program-to-list
  (lambda (l)
    (define exp-to-list
      (lambda (l)
	(cases expression l
	       (lit-exp (datum) datum)
	       (var-exp (id) id)
	       (primapp-exp (prim rands)
			    (list prim (let f ((rslt '()) (rands rands))
					 (if (null? rands)
					     rslt
					     (f (append rslt (list (exp-to-list (car rands))))
						(cdr rands))))))
	       (else
		(eopl:error 'exp-to-list
			    "Invalid expression " l)))))
    (cases program l
	   (a-program (exp)
		      (exp-to-list exp))
	   (else
	    (eopl:error 'program-to-list
			"Invalid application " l)))))

試験が以下。

(use gauche.test)

(add-load-path ".")
(load "program-to-list")

(test-start "program-to-list")
(test-section "program-to-list")
(test* "conversion example"
       '((incr-prim) (((add-prim) (3 x))))
       (program-to-list '(a-program
			  (primapp-exp
			   (incr-prim)
			   ((primapp-exp
			     (add-prim)
			     ((lit-exp 3)
			      (var-exp x))))))))

(test-end)

うーん。なんと言えば良いのか分かりませんが微妙。とりあえず OK ってコトにしておきたいと思います。