1. 程式人生 > >李巨集毅機器學習筆記——02.Where does the error come from ?

李巨集毅機器學習筆記——02.Where does the error come from ?

傳送門:

在上節課講到,如果選擇不同的function set就是選擇不同的model

在testing data上會得到不同的error,而且越複雜的model不見得會給你越低的error,我們要討論的問題就是error來自什麼地方?

error有兩個來源,偏差(bias)和方差(variance)

瞭解error的來源是重要的,因為常常做Machine Learing,做完就得到一個error value 接下來怎麼提高(improve)你的model',如果沒有什麼方向的話,也就沒有效率,如果可以診斷error的來源,就可以挑選適當的方法來improve你的model。

上一堂,我們做寶可夢進化後cp值的估測,也就是說我們要找一個function,input寶可夢,output就是進化後的cp值,這個function理論上有一個最佳的function,我們寫成\widehat{f},但這個理論上最佳的我們是不知道的,我們能做的是有一些training data,實際去抓一些寶可夢,然後根據training data所學出來的最好的function,為f^{*}。但這個f^{*}並不會真的等於\widehat{f},是\widehat{f}的估測值。可以想成現在是在打靶,\widehat{f}是靶的中心點,f^{*}是在靶子上的另外一個位置,f^{*}\widehat{f}中間有一段距離,這個距離可能來自於Bias,也有可能來自於Variance。

Bias和Variance到底是什麼呢?

假設我們現在有一個變數x,它的均值(mean)是\mu

,方差(variance)是\sigma ^{2}

估計它的均值,取樣n個點,再把n個點算平均值得到m,m不會跟\mu一樣,取樣算出好多m,如果把m的期望值算出,那麼m的期望值就會等於\mu,就好像是說如果在打靶的時候,準心是瞄準\mu的,由於種種原因,會散落在本來瞄準位置的周圍,散佈在周圍會有多散呢,取決於m的方差。

方差的值取決於去了多少個樣本,如果有比較多個n,它的散佈會比較集中,如果只取比較少的話,分散得比較開

如果要估測方差怎麼辦呢?

先用剛才的方法估測m,在計算方差s^{2},這個s^{2}可以估測\sigma ^{2}

 每次取出來的s^{2},它會散佈在\sigma ^{2}的周圍,它是屬於有偏估計量(Biased estimator),也就是說,如果去s^{2}的期望,它算出來並不是正好等於\sigma ^{2}

,所以普遍而言,s^{2}是比\sigma ^{2}還要小的,平均而言小的次數比較多,如果增加樣本量的話,\sigma ^{2}s^{2}之間估測的差距就越來越小。

也就是說,我們現在要估測的是靶的中心\widehat{f},這是我們的目標,做一次實驗,找出來的f^{*}如圖位置,這個位置跟紅心之間,有發生了兩件事,error取決於兩件事,

1、第一件事情是瞄準的位置在哪裡,也就是說估計量是不是偏差,

怎麼知道估計量是不是有偏差的?

f^{*}假設可以做很多次實驗,把f^{*}的期望值算出來,為\overline{f}。假設我們用右下角這個例子來看,\overline{f}如圖點,也就是說估計量跟靶心之間是有偏差的(Bias),也就說瞄的時候就沒有瞄準

2、另外一個error,你瞄準了這個位置,但是把子彈射出去以後還是會有偏移的,所以每次找出來f^{*}是不一樣的,而f^{*}跟算出來的\overline{f}的距離就是方差(Variance)

所以錯誤來自於兩件事,一件是Bias有多大, 另外一件是Variance有多大,所以最理想的狀況是,我們期待的是同時沒有Bias,Variance又小。

有一個問題,如何找很多個f^{*}呢,怎麼知道它的Bias和Variance有多大呢? 

所以假設說,這個世界上有很多個平行宇宙,在很多平行宇宙都在抓寶可夢,都想估計進化後的cp值,在每個平行宇宙抓到的寶可夢是不一樣的

如果拿不同的寶可夢找最好的function,就算用同一個model,假設都用y = b + w * x{cp}這個model,但是data不一樣,找出來的最好的function   f^{*}就是不一樣的,我們現在就是想知道它的散佈是怎樣的

所以我們就把100個不同宇宙的f^{*}都找出來,函式複雜度不同換另外的model,所找出來的f^{*}也不同。

所以如果我們看model之間的方差的話,只有考慮一次的model,它是比較集中的,如果考慮五次的話,就非常散了。所以如果用一個比較簡單的model,它的方差是比較小的,就好像說每次射擊的位置都是差不多的,如果換了比較複雜的model,方差很大,它的散佈就很開。

為什麼比較複雜的model它的散佈就比較開呢?

因為比較簡單的model受data的影響比較小,考慮一個比較極端的例子就一個function,f(x) = c,這個不管data怎樣,找出來的model都是一樣的

接下來來看bias

 Bias的意思是說,我們有很多很多f^{*},把f^{*}平均起來,找它的期望值\overline{f}\overline{f}跟靶心\widehat{f}有多接近呢。如果是一個大的Bias的話,意思是說,把所有的f^{*}平均起來,得到\overline{f}跟靶心是有一段距離的,如果是小的Bias的話,意思是說,f^{*}可能分散得很開,它的平均值\overline{f}跟靶心是接近的。

假設\widehat{f}如上圖,所以寶可夢的資料就是從這一條曲線隨機出來的,每次隨機10個點出來,那就可以找一個f^{*}

這是試驗結果,黑色的線代表的靶心,是真正的\widehat{f};紅色代表做5000次試驗,每次找出來的f^{*}都是不一樣的;藍色代表把5000f^{*}平均變成\overline{f},右上角是隻考慮一次式,左邊是隻考慮三次式,右下角式只考慮五次式,五次式平均變成的\overline{f}跟真正的\widehat{f}是接近的。

所以說如果是一個比較簡單的model,它有比較大的方差,如果是一個比較複雜的model,但它有比較小的方差。所以左邊這個簡單的model,它的case每一次f^{*}都差不多,它分佈比較小,但它跟靶心是有差距的,右邊的case,每一次找出來的f^{*}都不太一樣,但平均而言是在靶心中間

為什麼會這樣呢?

直觀的講,我們的model就是一個function set,用範圍來表示這個function set ,當你定義個意model的時候,你就已經設定好你最好的function就只能從function set裡面挑出來,如果是一個簡單的model它的space是比較小的,它可能就沒有包含目標(target),在沒有包含目標的情況下,不管怎麼sample都沒用的;但是如果model是比較複雜的,model所代表function space是比較大的,它可能有包含目標,只是它沒有辦法找出那個target在哪裡,因為給的training data 不夠,每次給的training data都不一樣,所以每次找的f^{*}都不一樣,但如果它們是散佈在這個目標附近的,平均起來就可以得到\overline{f}

回到上次看到model對testing data error所畫出來的線,比較簡單的model它的Bias 比較大,但是方差比較小;比較複雜的model就是Bias 比較小,但方差比較大。

所以這個圖,由左到右,model的Bias所造成的error是逐漸下降,同時Variance是越來越大 ,所以當這兩項同時被考慮的時候,得到的就是藍色這條線。 

如果error來自於Variance很大,這個狀況就是過擬合(overfitting),如果error來自於Bias很大,這個狀況叫做欠擬合(underfitting)。

你現在的問題是Bias大還是Variance大?

你應該先知道這件事情,未來工作要提升model的時候,應該要走哪一個方向,怎麼知道是Bias大還是Variance大呢

如果你的model沒有辦法fit訓練資料的時候,代表說Bias是大的,如果我們只隨機抽取這幾個藍色的點,而model沒有辦法fit少數幾個藍色的點,代表說你的model跟正確的model是有一段差距的,這個時候是underfitting;如果你可以fit訓練資料,在訓練資料得到小的error,但是在tessting data上卻得到一個大的error,這意味著你的model可能是Variance比較大,這個時候代表的是overfitting。遇到bias和variance,其實是要用不同的方式來處理它的,如果是Bias大,應該重新設計你的model,bias大代表說現在的model裡可能根本沒有包含你的target。

如果是Variance大的話,①增加data,是很有效控制Variance的方法,②正則化 ,找出來的曲線越平滑越好,這個時候可能會傷害Bias,調整了function space,只包含了哪些比較平滑的曲線,可能就沒有辦法包含\widehat{f}

所以我們現在遇到的問題是,我們有很多個model可以選擇,引數可以調,通常我們是在Bias和Variance之間做一些平衡,我們希望找一個model,variance夠小,bias也夠小,這樣合起來,給我們最小的testing data的error

我們需要另外找一個測試資料,是沒有用過的

拿作業舉例

怎麼樣做才是可靠呢?

把training set 分成兩組,一組是真正拿來做model,另外一組不拿來train model,拿它來選model,在training set找出最好的function f^{*},才用Validation set來選擇model,然後用全部的training set 再在model 3上訓練一次,這個時候在public上面的error才能夠真正反映private 上面的error

如果你不相信某一次train 跟test 結果的話,那就分很多種不同的樣子,N倍的交叉驗證,比如說把training set 分成三份,每一次拿其中一份當作Validation set,另外兩份做training,如果知道哪一個model比較好的話,就把這三個model統統在這一個情景下算一下error,然後算一下avg err,然後發現在這三個情況下是model1 最好,把model1再訓練完整的training set,然後再在testing set上面。

傳送門: