Skip to content

Instantly share code, notes, and snippets.

@leesharma
Created October 24, 2017 15:15
Show Gist options
  • Save leesharma/250c3dfd18b5618fb7bf53ab7bbcde1d to your computer and use it in GitHub Desktop.
Save leesharma/250c3dfd18b5618fb7bf53ab7bbcde1d to your computer and use it in GitHub Desktop.
A working example of symbolic differentiation (SICP section 2.4).
;Symbolic Differentiation
;
; note: all arithmetic terms must have two operands!
; e.g. `(+ a b c) becomes `(+ a (+ b c)))
;
(define (deriv exp var)
(cond ((constant? exp var) 0)
((same-var? exp var) 1)
((sum? exp)
(make-sum (deriv (a1 exp) var)
(deriv (a2 exp) var)))
((product? exp)
(make-sum
(make-product (m1 exp)
(deriv (m2 exp) var))
(make-product (deriv (m1 exp) var)
(m2 exp))))))
(define (constant? exp var)
(and (atom? exp)
(not (eq? exp var))))
(define (same-var? exp var)
(and (atom? exp)
(eq? exp var)))
(define (sum? exp)
(and (not (atom? exp))
(eq? (car exp) '+)))
(define (make-sum a1 a2)
(cond ((and (number? a1)
(number? a2))
(+ a1 a2))
((and (number? a1) (= a1 0)) a2)
((and (number? a2) (= a2 0)) a1)
((eq? a1 a2) (list '* 2 a1))
(else (list '+ a1 a2))))
(define a1 cadr)
(define a2 caddr)
(define (product? exp)
(and (not (atom? exp))
(eq? (car exp) '*)))
(define (make-product m1 m2)
(cond ((and (number? m1) (number? m2)) (* m1 m2))
((and (number? m1) (= m1 1)) m2)
((and (number? m2) (= m2 1)) m1)
((and (number? m1) (= m1 0)) 0)
((and (number? m2) (= m2 0)) 0)
(else (list '* m1 m2))))
(define m1 cadr)
(define m2 caddr)
(define (atom? x)
(not (list? x)))
;Example equation
(define foo
'(+ (* a (* x x))
(+ (* b x)
c)))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment