SICP 習題 (1 35)解題總結

2021-09-06 15:29:24 字數 4318 閱讀 1535

sicp 習題 1.35要求我們證明**切割率φ 是變換函式 x => 1+ 1/x 的不動點,然後利用這一事實通過過程fixed-point 計算出φ的值。

首先是有關函式的不動點,這個概念須要理解清晰,後面好幾道題都是環繞函式不動點展開的。作者在這裡設計這些習題的原因也是希望讀者能夠關注函式不動點。

事實上有關不動點這個東西我在做習題「1.8」的時候就認為好奇了。為什麼「(x+x/y)/2」會不斷逼近x的平方根呢?又為什麼「(x/y2+2y)/3」會不斷逼近x的立方根呢?

當時僅僅顧著做題,就沒有深入去考慮,經過1.35開始的幾道題才開始對函式的不動點有了一些理解,反過來就認為習題「1.8」裡提到的逼近x的立方根的方法比較easy理解了。

要完成這裡的幾道習題,大家首先須要讀完書中的1.3.3這一節,裡面有函式不動點的描寫敘述。事實上,1.3.3節中的內容是想說明過程(或者說函式)能夠被看作一般性的方法,對過程的通性進行討論。僅僅是,作者可能認為用函式不動點這個例子能夠非常好地展示過程的通性,所以使用了函式不動點作為例子。對於函式的不動點,我們能夠無論過程的內在實現,而在過程外部通過乙個一般性的方法求得這些過程的不動點。當然,不是全部函式都有不動點,所以這種方法並非對全部函式生效的。

那麼,更進一步須要了解的就是:什麼是函式的不動點?

書中是這樣描寫敘述的:

假設有x滿足f(x)=x,那麼x就稱之為函式f()的不動點。

聽起來有點抽象,不太好理解,假設我們用以下的例子可能就比較easy理解了。

我們假設眼下流行的南韓整容技術是乙個函式,叫「整容()」,那麼我們非常easy理解以下的等式:

整容(醜女)= 美女

就是乙個醜女送進手術室,通過「整容」函式的處理,輸出的是乙個美女。

可是,事實上的整容沒有那麼easy,須要一點一點去整,所以我們的函式應該像以下這樣:

整容(醜女)= 美一點的醜女

假設我們把「美一點的醜女」送去整容,會有:

整容(美一點的醜女)= 更美一點的醜女

於是乎,假設我們有函式:

整容(整容(整容 ......(整容(整容(整容(整容(醜女)))))))

那麼結果就應該非常接近美女了。

最終,假設我們把美女送去整容,出來的還是美女,就是說

整容(美女)= 美女

這個時候就是f(x)=x的時候了,就是說「美女」就是函式「整容」的不動點!

這樣你應該能夠理解什麼是函式的不動點了吧?

理解了函式的不動點,我們再來看看怎樣求出乙個函式的不動點。還是用整容的例子,方法比較簡單粗暴,就是把隨便乙個人送去整容,進去之前和送出來後都拍個**,假設兩張**相差比較大,就說明這個人整容的空間還比較大,弄進去再整,直到進去之前和出來之後看不出什麼區別了,那麼這個結果就是「整容」函式的不動點了!

假設說「全智賢」是南韓整容界公認的典型美女的話,你隨便抓乙個人,無論性別,送去給南韓整容醫生不斷整容,最後出來的都長成「全智賢」那樣。

我們就得出了「南韓整容」函式的不動點,那就是「全智賢」!

進一步考察的話,你會發現這個尋找函式不動點的方法和函式本身沒太大關係,「整容」的函式能夠用這種方法,「健身」的函式也一樣,「server調優」的函式也一樣,基本思路就是不斷反覆呼叫這個函式,直到這個函式對目標不再起作用為止。

這樣就能夠理解書中的fixed-point函式了:

(define tolerance 0.00001)

(define (fixed-point f first-guess)

(define (close-enough? v1 v2)

(< (abs (- v1 v2 )) tolerance))

(define (try guess)

(let (( next (f guess)))

(if (close-enough? guess next)

next

(try next))))

(try first-guess))

fixed-point函式的作用就是用first-guess作為初始材料,不斷呼叫函式f對它進行加工,直到f函式的輸入值和輸出值close-enough為止。

這時候回過來考察1.1.7章的求平方根的函式就有清晰的思路了。

書中提到,假設我們希望求乙個數x的平方根,就是要求乙個y,使得y^2 = x,由y^2=x推導出乙個等式y=x/y,所以我們要求的是變換x => x/y的不動點。

這種描寫敘述方式對數學高手們是如此簡單,僅僅是對於我等數學白痴來講還是不好理解。

我對於求平方根的方法的理解過程是這種。

首先我們把問題簡化一下,求x的平方根變為求乙個已知數的平方根,比方求10的平方根。

這種話我們要求的事實上是乙個x,使x * x =10。

或者說是求x1 * x2= 10,同一時候x1= x2。

假設要讓x1 * x2=10的條件滿足,那麼就有x1 = 10 / x2,這個簡單的數學轉換就好理解了吧。

接著,假設我們設計乙個函式f(x)是這種 f(x) = 10/x,上面的等式就能夠寫成以下這樣:

x1 = 10 / x2 = f (x2)

也就是 x1 = f (x2)

假設我們找到了函式f(x)的不動點,就有f(x)= x,就是有:

x1=f(x2) = x2

這時候就是x1=x2的時候了。

恭喜一下你自己吧!你找到求10得平方根的方法了!

僅僅是。。。。。可惜的是,就像書中說的,變換x => 10/ x並不收斂!

簡單說就是函式f(x)= 10/x沒有不動點!

假設上面這些x1,x2不正確你胃口,你還是不理解的話,想象一下以下的場景:

假設你是乙個整容醫生,須要對人的眼睛進行整容,而高手告訴你的秘訣是兩個眼睛長度的乘積等於10的時候就是最漂亮的一雙眼睛,你會怎麼做呢?

首先你有個常識,就是左右眼要一樣大才行,不然整成大小眼了。當今你要做的就是按高手的秘籍整,直到兩個眼睛一樣大為止。

好,我們這些笨整容醫師們,開始手術啦!

有個人來了,量量他的左眼,嘻嘻,左眼長度2cm!啊,多麼小的眼睛呀。

那麼,按秘籍算一算右眼應該是多大呢?10/2=5!右眼5cm就好了!

手術過後看看完了!大小眼!左眼2cm,右眼5cm。

這不行,把左眼搞成跟右眼一樣吧,也是5cm!

再按秘籍算一算右眼應該是多長?左眼5cm,10/5=2,右眼2cm就好了!

手術過後再看!還是大小眼!左眼5cm,右眼2cm。

繼續整!

哈!沒完沒了了!人給你整殘了你也做不完!

這就叫乙個不收斂的變換!

咋辦哩?

用書上說到的「平均阻尼」術!

假設你發現乙個人左眼2cm,右眼5cm,合理的眼睛長度應該是兩個眼睛長度的平均數吧!

應該是(2+5)/2,那就是3.4cm

假設左眼搞成3.4cm長,按秘籍計算的話,右眼應該是10/3.4=2.94左右。

左眼3.4cm,右眼2.94cm,還是大小眼,繼續平均一下,眼睛長度應該是(3.4+2.94)/2 吧,大概是3.17.

這就對了嘛,越來越接近了。

所以 x => (x + x/10)/2 這個變化是收斂的。

我們最終能夠整出一對漂亮的雙眼了! (上帝呀,千萬不要讓技術男去做整容醫師呀。)

回到題目的本身,題目是要求我們證明**切割率 φ 是變換函式 x => 1+ 1/x 的不動點。

**切割率φ是什麼?翻回書上的1.2.2節先看看:

φ=1.6180

他是怎麼求出來的呢,他是按等式φ^2=φ+1求出來的。

也就是說,假設有x^2=x+1,那麼x就是**切割率。

事實上兩個都對,所謂**切割,就是把乙個線段ab分成兩段,各自是ao和ob,假設ab/ao=ao/ob,那麼這個線段ab就被「**切割」了,這時候假設我們把**切割率記錄成ab/ao就是1.618,反過來假設我們記錄成ao/ab就是0.618,這也是**切割率迷人的地方,由於1/1.618=0.618。

好,方便起見,我們就用x^2=x+1這個表示式吧,我們要證明函式1+1/x的不動點x滿足x^2=x+1。

有了上面的一系列分析,你會發現問題不是太難。

我們有乙個函式f(x)=1+1/x,還是用x1和x2兩個數,x1表示函式輸出,x2表示函式輸入,就有:

x1=1+1/x2

當我們找到函式f(x)=1+1/x的不動點的時候,意味著f(x)=x,就是說x1=x2。

上面的等式就變為x1=1+1/x1,這時候兩邊都乘以x1,就有x1^2=x1+1。

哈哈,就是說函式f(x)=1+1/x的不動點x滿足方程x^2=x+1,滿足方程x^2=x+1的就是φ!

題目的後半部分還要求我們依據這個事實使用fixed-point函式求φ,這就簡單了

(fixed-point (lambda (x) (+ 1 (/ 1 x))) 1)

SICP 習題 1 14 解題總結

sicp 習題 1.14要求計算出過程count change的增長階。count change是書中1.2.2節講解的用於計算零錢找換方案的過程。要解答習題1.14,首先你需要理解count change的工作方式,要理解count change的工作方式,最好是自己去實現一遍count chan...

SICP 習題 1 22 解題總結

sicp 習題 1.22 要求改進題中列舉出來檢查素數的過程,用來求1000,10000,100 000,還有1000 000附近的素數,然後比較求這些素數的時間,看是否符合 n 的複雜度。要完成這道題首先要將題目中列出的過程照抄到你的scheme環境中。因為書中的 使用了 runtime 過程,我...

SICP 習題 1 25 解題總結

sicp 習題 1.25 就是我上面說過的傷自尊的題了。習題1.25說到有個叫allyssa p.hacker的人說expmod過程完全沒有必要搞那麼麻煩,直接使用前面的fast expt過程和remainder過程就好了,她 叫alyssa的應該是女的吧 覺得可以這樣定義expmod define...