sicp每日一題[2.56]

再思即可發表於2024-10-24

Exercise 2.56

Show how to extend the basic differentiator to handle more kinds of expressions. For instance, implement the differentiation rule

d(x^n)/dx = n x^(n-1)

by adding a new clause to the deriv program and defining appropriate procedures exponentiation?, base, exponent, and make-exponentiation.
(You may use the symbol ** to denote exponentiation.) Build in the rules that anything raised to the power 0 is 1 and anything raised to the power 1 is the thing itself.


這道題難度不大,先仿照 make-sum, make-product 寫出 make-exponentiation 函式,剩下的部分就很簡單了。

(define (make-exponentiation base exponent)
  (cond ((=number? base 0) 0)
        ((=number? base 1) 1)
        ((and (number? base) (=number? exponent 0)) 1)
        ((and (number? base) (=number? exponent 1)) base)
        ((and (number? base) (number? exponent)) (* base (make-exponentiation base (- exponent 1))))
        (else (list '** base exponent))))

(define (exponentiation? x) (and (pair? x) (eq? (car x) '**)))

(define (base e) (cadr e))

(define (exponent e) (caddr e))

(define (deriv exp var)
  (cond ((number? exp) 0)
        ((variable? exp) (if (same-variable? exp var) 1 0))
        ((exponentiation? exp)
         (let ((base (base exp))
               (n (exponent exp)))
           (if (same-variable? base var)
               (make-product n
                             (make-exponentiation base (- n 1)))
               0)))
        ((sum? exp) (make-sum (deriv (addend exp) var)
                              (deriv (augend exp) var)))
        ((product? exp)
         (make-sum
          (make-product (multiplier exp)
                        (deriv (multiplicand exp) var))
          (make-product (deriv (multiplier exp) var)
                        (multiplicand exp))))
        (else
         (error "unknown expression type: DERIV" exp))))


(deriv '(** x 3) 'x)
(deriv '(** x 3) 'y)

; 執行結果
'(* 3 (** x 2))
0

相關文章