sicp ex-2.57 多項式求導
阿新 • • 發佈:2018-12-31
運算 gen append 答案 功能 add can define 並且
原書正文中列舉了怎樣對二項式求導的方法,本習題要求修改求導函數支持以支持多項式求導。
主要修改在於取 +/* 運算的第二個運算數:如果剩余的運算數大於1,則返回一個列表,並且在列表前加 +/* 運算符。
這道題在網上查了很久,沒找到滿意的答案,自己動手寫一個,功能驗證正確。
測試用例:
(derive ‘(+ y x) ‘x)
(derive ‘(+ y x 3) ‘x)
(derive ‘(+ y x (+ x 4) 3) ‘x)
(derive ‘(+ (* x x) (* 3 x) y) ‘x)
(derive ‘(+ (* x x) (* 3 x)) ‘x)
(derive ‘(+ (* x x x (+ 1 (* x x))) (* 3 x)) ‘x)
運行結果:
1
1
2
‘(+ (+ x x) 3)
‘(+ (+ x x) 3)
‘(+ (+ (* x (+ (* x (+ (* x (+ x x)) (+ 1 (* x x)))) (* x (+ 1 (* x x))))) * x x (+ 1 (* x x)))) 3)
代碼如下:
(define (derive exp var) (define (=number? a b) (and (number? a) (= a b))) (define (make-sum a b) (cond ((=number? a 0) b) ((=number? b 0) a) ((and (number? a) (number? b)) (+ a b)) (else (list ‘+ a b)))) (define (make-product a b) (cond ((=number? a 0) 0) ((=number? b 0) 0) ((=number? a 1) b) ((=number? b 1) a) ((and (number? a) (number? b)) (* a b)) (else (list ‘* a b)))) (define (product? a) (if (eq? a ‘*) true false)) (define (sum? a) (if (eq? (car a) ‘+) true false)) (define (addend s) (cadr s)) (define (make-sum-list a b) (if (= (length b) 1) (list ‘+ a (car b)) (append (list ‘+ a ) b)) ) (define (augend s) (if (<= (length s) 3) (caddr s) (make-sum-list (caddr s) (cdddr s)))) (define (make-product-list a b) (if (= (length b) 1) (list ‘* a (car b)) (append (list ‘* a ) b)) ) (define (multiplier s) (cadr s)) (define (multiplicand s) (if (<= (length s) 3) (caddr s) (make-product-list (caddr s) (cdddr s)))) (define (variable? a) (symbol? a)) (cond ((number? exp) 0) ((variable? exp) (if (eq? exp var) 1 0)) ((sum? exp) (make-sum (derive (addend exp) var) (derive (augend exp) var))) ((product? (car exp)) (make-sum (make-product (multiplier exp) (derive (multiplicand exp) var)) (make-product (derive (multiplier exp) var) (multiplicand exp))))))
sicp ex-2.57 多項式求導