i5.scm 1.3 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. #lang racket
  2. (require racket/match)
  3. (define builtins
  4. `((car . ,car)
  5. (cdr . ,cdr)
  6. (cons . ,cons)
  7. (list . ,list)
  8. (list . ,list?)
  9. (null? . ,null?)
  10. (+ . ,+)
  11. (- . ,-)
  12. (* . ,*)
  13. (/ . ,/)
  14. (= . ,=)
  15. (eq? . ,eq?)
  16. (equal? . ,equal?)
  17. (not . ,not)))
  18. (define special-forms
  19. '(lambda if quote and or))
  20. (define (i exp env spec)
  21. (match exp
  22. ((? number? n) n)
  23. ((? boolean? b) b)
  24. ((? symbol? s)
  25. (cond ((assoc s env) => cdr)
  26. (else (error "unbound variable" s))))
  27. ((? list? l)
  28. (if (member (car l) spec)
  29. (i-special l env spec)
  30. (apply (i (car l) env spec)
  31. (map (lambda (exp) (i exp env spec)) (cdr l)))))
  32. (else (error "unknown expression type" exp))))
  33. (define (i-special exp env spec)
  34. (match exp
  35. (`(if ,t ,c ,a)
  36. (if (i t env spec)
  37. (i c env spec)
  38. (i a env spec))
  39. (`(lambda (,x) ,b)
  40. (lambda (y)
  41. (i b (cons (cons x y) env) (remove x spec))))
  42. (`(quote ,d)
  43. d)
  44. (`(and . ,things)
  45. (let loop (things things)
  46. (if (null? things)
  47. #t
  48. (if (i (car things) env spec)
  49. (loop (cdr things))
  50. #f))))
  51. (`(or . ,things)
  52. (let loop (things things)
  53. (if (null? things)
  54. #f
  55. (if (i (car things) env spec)
  56. #t
  57. (loop (cdr things))))))
  58. (else (error "Unimplemented special form:" exp))))