演算子として '* および '+ を使用した 2 項式があると仮定すると、単純化される式の再帰的降下を使用して代数の基本ルールをエンコードするのは簡単です。そのとおり:
(define (simplify exp)
(cond ((number? exp) exp)
((symbol? exp) exp)
((list? exp)
(assert (= 3 (length exp)))
(let ((operator (list-ref exp 0))
(operand-1 (simplify (list-ref exp 1))) ; recurse
(operand-2 (simplify (list-ref exp 2)))) ; recurse
(case operator
((+)
(cond ((and (number? operand-1) (= 0 operand-1)) operand-2)
((and (number? operand-2) (= 0 operand-2)) operand-1)
((and (number? operand-1) (number? operand-2))
(+ operand-1 operand-2))
(else `(,operator ,operand-1 ,operand-2))))
((*)
(cond ((and (number? operand-1) (= 0 operand-1)) 0)
((and (number? operand-2) (= 0 operand-2)) 0)
((and (number? operand-1) (= 1 operand-1)) operand-2)
((and (number? operand-2) (= 1 operand-2)) operand-1)
((and (number? operand-1) (number? operand-2))
(* operand-1 operand-2))
(else `(,operator ,operand-1 ,operand-2))))
(else 'unknown-operator))))
(else 'unknown-expression)))
これは、式に対して 1 つのパスのみを実行します。通常、結果が変わらなくなるまでパスを実行する必要があります。