[tensorflow] MNIST 使用 softmax regression

這篇是將這本書(實戰TensorFlow|Google深度學習系統)的第三章範例做一個整理,其實書裡已經講的很好了。

MNIST(Mixed National Institute of Standards and Technology database)是手寫數字的圖片辨識資料集,數字就是0-9,總共10個類別。

首先要載入資料,載入以後會建立 MNIST_data資料夾,裡面會有這幾個檔案:

one-hot=True 是表示類別的編碼方法,因為類別共10類,如果是第8類,就表示為[0,0,0,0,0,0,0,1,0,0]。

資料就是分成images跟labels,labels就是註明這張影像的內容是數字多少,資料集會分成train、test跟validation三塊,這是機器學習的標準做法。我們可以來看一下相關資訊:

55000、10000跟5000是數量,那784是什麼? 是維度。MNIST的影像是28×28=784,所以在這裡就表現為784維。

什麼是softmax呢?

https://zh.wikipedia.org/wiki/Softmax%E5%87%BD%E6%95%B0

在數學,尤其是機率論和相關領域中,Softmax函數,或稱歸一化指數函數,是邏輯函數的一種推廣。它能將一個含任意實數的K維的向量 z的「壓縮」到另一個K維實向量 σ(z) 中,使得每一個元素的範圍都在(0,1)之間,並且所有元素的和為1。

有看沒有懂?其實就是做正規化啦,每個東西都變成exp,然後再來做正規化。那我們如果把類神經網路(NN)看成是「對於輸入值做一連串的線性操作」,那麼,我們就可以將整件事情寫成數學式: y=softmax(Wx+b),其中x是輸入向量,W是權重,b是係數,因為x、W跟b都是多維度的,所以最後變成一個矩陣相乘,我們的目的就是

讓正確的類別對應到的值最大

回到tensorflow,首先要先把tensorflow載入,我們依慣例命名為tf,你要取名wtf也可以。然後建立一個InteractiveSession,顧名思義是一個互動式的session。

來看一下tensorflow的官方文件對InteractiveSession的定義:

A TensorFlow Session for use in interactive contexts, such as a shell.

The only difference with a regular Session is that an InteractiveSession installs itself as the default session on construction. The methods tf.Tensor.eval and tf.Operation.run will use that session to run ops.

然後你的疑問就變成「啊什麼是session」,

A class for running TensorFlow operations.

A Session object encapsulates the environment in which Operation objects are executed, and Tensor objects are evaluated.

tensorflow的計算是透過一堆圖,圖裡面有一堆節點一堆邊,每個節點代表了一種操作的實體,計算的過程就是資料沿著邊,跑到節點,被揍一揍整個型,再沿著下一個邊跑去其它節點,這樣的資料稱為tensor(依wiki的定義,tensor是定義成某個向量空間或其對偶空間上的多重線性映射),這樣的動作稱為flow,合起來就叫做tensorflow。這個圖的操作過程,我們把它封裝起來,就是一個session。

好了再來要把資料載入

placeholder的參數有三個,dtype、shape、name,這裡我們只需用前兩個。shape就是在講維度,這裡的[None, 784]的意思是不限制資料數量的784維。

再來要開始對softmax regression的參數W跟b做定義,

輸入的資料是幾維? 784維,輸出的類別有10個,所以W是784×10,而b只對應到類別,所以是10。這裡我們將W跟b都初始化為0。

softmax模型在tensorflow裡面有定義了,所以要用的時候就是

tf.nn是一堆類神經網路的東西,softmax是它的一個函數。matmul是matrix multiplication,矩陣乘法。

是不是覺得很無感?正常的,人家都幫你寫好了, 你只要把變數餵給他就好。

再來,機器學習的學習過程中,關鍵之一是要學對,怎麼知道對不對?用考試,看你跟滿分差多少,這就是loss function/cost function/fitness function的目的。在這裡我們的目的是要讓差距縮小,書上是用cross-entropy,那我們也用cross-entropy。

cross-entropy的介紹可以參考https://en.wikipedia.org/wiki/Cross_entropy

softmax該有的參數有了,loss function也有了,最後就是一個決定權重調整的函數,這裡用SGD (stochastic Gradient Descent)。

0.5是GradientDescentOptimizer的參數,最小化的目標是我們在上面定義的cross_entropy。

再來將variables做初始化:

學習是一種反覆的操作,操作的作法是從訓練集裡面一次抓100筆來建構一個mini-batch,餵給placeholder,再呼叫我們前面定義的train_step。

train_step是我們上面定義的,那run()是什麼鬼?其實 train_step.run() 就是 tf.get_default_session().run(train_step)的縮寫啦。

這個迴圈就是在跑學習的過程,如果有用GPU,像我用GTX1080,大概2秒吧。

學完了訓練完了,再來就是要看表現如何:

其中, tf.argmax(y,1) 的意思是,從y裡面找最大值的位置出來,如果最大值出現在8的位置就回傳8。然後用equal去判斷y跟y2這兩個的結果有沒有一樣。不要忘記y是真實的答案,y2是我們算出來的。每一張測試資料都有一個正確值,那一大堆測試資料要看什麼?看平均啊:

cast是要把上面定義的correct_prediction的值從整數換成float32,然後再用reduce_mean求平均值。定義完了之後就可以看結果了

這裡是把測試影像以x表示,把答案用y2表示,在這裡,a.eval是tf.get_default_session().run(a)的一種縮寫,意思跟下面這個一樣:

我這裡是印0.9202,就這樣就跑完了MNIST的教學導覽啦。

 

參考資料

1. https://stackoverflow.com/questions/38987466/eval-and-run-in-tensorflow

2.  https://www.tensorflow.org/api_docs/

3. https://kknews.cc/zh-tw/tech/ya9g3kk.html

Leave a Reply

你的電子郵件位址並不會被公開。 必要欄位標記為 *