在 TensorFlow 之中使用卷積神經(jīng)網(wǎng)絡(luò)
在之前的學(xué)習(xí)過程之中,我們已經(jīng)使用過卷積神經(jīng)網(wǎng)絡(luò),但是我們并沒有真正的了解該網(wǎng)絡(luò)的原理以及詳細(xì)的使用規(guī)則。因此這節(jié)課我們便學(xué)習(xí)以下什么是卷積神經(jīng)網(wǎng)絡(luò),并且了解如何在 TensorFlow 之中使用卷積神經(jīng)網(wǎng)絡(luò)。
1. 什么是卷積神經(jīng)網(wǎng)絡(luò)
卷積神經(jīng)網(wǎng)絡(luò),Convolutional Neural Network,簡(jiǎn)稱 CNN ,是一種在圖像領(lǐng)域最常使用的一種神經(jīng)網(wǎng)絡(luò)。
卷積神經(jīng)網(wǎng)絡(luò)總體來說可以分為三個(gè)部分:
- 卷積層:用于提取數(shù)據(jù)的特征;
- 池化層:對(duì)提取的特征的規(guī)模進(jìn)行縮小,減少運(yùn)算量;
- 全連接層:FC 層,在 TensorFlow 之中就是 Dense 層。
卷積層最常用的作用就是用來 “提取特征”,也就是將二維數(shù)據(jù)的 “特征” 提取出來,而我們最常使用的二維數(shù)據(jù)就是圖片數(shù)據(jù)。
那么什么是特征?簡(jiǎn)單來說,特征就是數(shù)據(jù)中所包含的信息,我們對(duì)一個(gè)數(shù)據(jù)進(jìn)行分類,利用的就是它的所包含的信息進(jìn)行分類。而特征的形式多種多樣,可以是二維向量,也可以是三維向量,當(dāng)然也可以是一維向量。
2. 卷積層的原理
要進(jìn)行專業(yè)的原理解釋需要很多的數(shù)學(xué)推算,這里以平常最常見的二維卷積對(duì)圖片進(jìn)行處理為例進(jìn)行說明。
說到卷積層,就不得不談起卷積層的最重要的一個(gè)概念:卷積核。
卷積核可以看作是一個(gè)算子,它會(huì)對(duì)圖片數(shù)據(jù)的每個(gè)像素進(jìn)行一次遍歷,并且得到一個(gè)新的數(shù)據(jù)。
比如說,我們目前有一個(gè)圖片數(shù)據(jù),它的具體的數(shù)據(jù)為如下所示,其中每個(gè)數(shù)據(jù)表示一個(gè)像素點(diǎn)的數(shù)據(jù)。
1 2 1 2 0
0 2 3 4 5
4 2 0 1 3
1 1 2 3 4
5 0 0 1 2
假如我們的卷積核為:
1 0 1
0 1 0
1 0 1
那么卷積核會(huì)從左上角開始掃描,按照從左到右,從上到下的順序進(jìn)行掃描。
對(duì)于每一次掃描,得到的結(jié)果為:
結(jié)果 = 求和(卷積核每個(gè)位置的系數(shù) * 掃描區(qū)域之中對(duì)應(yīng)位置的數(shù)據(jù))
比如對(duì)于第一次掃描,掃描區(qū)域?yàn)椋?/p>
1 2 1
0 2 3
4 2 0
那么我們得到結(jié)果為
1*1 + 2*0 + 1*1 +
0*0 + 2*1 + 3*0 +
4*1 + 2*0 + 0*1 = 8
用動(dòng)畫形式展示來說就是 (圖片來源于鏈接):
3. 池化層的原理
池化層的原理相對(duì)而言比較簡(jiǎn)單,它和卷積層一樣,都包括一個(gè)算子,只不過該算子在掃描的過程之中不會(huì)經(jīng)過之前掃描的部分,也就是說每個(gè)數(shù)據(jù)只會(huì)被掃描一遍。
用動(dòng)畫形式展示來說就是 (圖片來源于鏈接):
不同的池化方法對(duì)應(yīng)著不同的池化層,我們最常使用的是最大池化與平均池化:
- 最大池化:取掃描區(qū)域的最大值;
- 平均池化:取掃描區(qū)域的平均值。
3. 如何在 TensorFlow 之中使用卷積神經(jīng)網(wǎng)絡(luò)
1. 如何在 TensorFlow 之中使用卷積層
在 TensorFlow 之中,使用卷積層的具體 API 為:
tf.keras.layers.Conv2D(
filters, kernel_size, strides=(1, 1), padding='valid',
dilation_rate=(1, 1), activation=None, ......)
其中我們最常用的參數(shù)的具體含義包括:
- filters:得到特征的通道數(shù)量,比如一般 RGB 的通道為 3 ,我們可以指定 filter 來輸出指定通道數(shù)量的特征;
- kernel_size:卷積核的大小,也就是算子的大小,可以為一個(gè)二維元組,也可以是一個(gè)整數(shù)(此時(shí)卷積核為正方形);
- strides=(1, 1):卷積核移動(dòng)的步伐,一般每次向右移動(dòng)一格,每行向下移動(dòng)一格,我們可以手動(dòng)指定移動(dòng)的步伐的大小。
- padding=‘valid’:是否使用 Padding ,也就是說是否在原來數(shù)據(jù)的四周再加上一圈數(shù)據(jù),這樣可以讓原圖片的每個(gè)像素都在卷積核中央,可以選擇為 valid 或者 same ;
- dilation_rate=(1, 1):是否采用空洞卷積,很少使用,只有在擴(kuò)大視野的時(shí)候使用,這里不再展開描述;
- activation=None:激活函數(shù),和我們之前接觸的卷積函數(shù)一樣。
2. 如何在 TensorFlow 之中使用池化層
在 TensorFlow 之中,使用池化層的具體 API 為:
tf.keras.layers.MaxPool2D(
pool_size=(2, 2), strides=None, padding='valid', ...
)
其中我們最常用的參數(shù)與卷積層類似,它們的具體含義包括:
- pool_size: 池化算子的大小,和卷積層的 kernel_size 相似;
- strides: 步伐大小,與卷積層的 strides 相同含義;
- padding:是否進(jìn)行填充,可以選擇 valid 或者 same 。
3. 一個(gè)具體的卷積神經(jīng)網(wǎng)絡(luò)
由于我們?cè)谥皩W(xué)習(xí)之中已經(jīng)采用過卷積神經(jīng)網(wǎng)絡(luò)進(jìn)行訓(xùn)練,因此同學(xué)們可以使用之前的數(shù)據(jù)進(jìn)行訓(xùn)練,這里只是給出一個(gè)簡(jiǎn)單的網(wǎng)絡(luò)模型,以及它的結(jié)構(gòu):
import tensorflow as tf
model = tf.keras.models.Sequential([
tf.keras.layers.Conv2D(32, (3, 3), activation='relu', input_shape=(32, 32, 3)),
tf.keras.layers.MaxPooling2D((2, 2)),
tf.keras.layers.Conv2D(64, (3, 3), activation='relu'),
tf.keras.layers.MaxPooling2D((2, 2)),
tf.keras.layers.Conv2D(128, (3, 3), activation='relu'),
tf.keras.layers.Flatten(),
tf.keras.layers.Dense(128, activation='relu'),
tf.keras.layers.Dense(64, activation='relu'),
tf.keras.layers.Dense(10, activation='softmax')])
model.summary()
我們可以得到數(shù)據(jù)為:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
conv2d_5 (Conv2D) (None, 30, 30, 32) 896
_________________________________________________________________
max_pooling2d_3 (MaxPooling2 (None, 15, 15, 32) 0
_________________________________________________________________
conv2d_6 (Conv2D) (None, 13, 13, 64) 18496
_________________________________________________________________
max_pooling2d_4 (MaxPooling2 (None, 6, 6, 64) 0
_________________________________________________________________
conv2d_7 (Conv2D) (None, 4, 4, 128) 73856
_________________________________________________________________
flatten_4 (Flatten) (None, 2048) 0
_________________________________________________________________
dense_15 (Dense) (None, 128) 262272
_________________________________________________________________
dense_16 (Dense) (None, 64) 8256
_________________________________________________________________
dense_17 (Dense) (None, 10) 650
=================================================================
Total params: 364,426
Trainable params: 364,426
Non-trainable params: 0
_________________________________________________________________
在這個(gè)模型之中,我們默認(rèn)輸入的圖像數(shù)據(jù)為 32*32 大小,并且擁有三個(gè)通道。在該模型之中,我們使用了三個(gè)二維卷積層與兩個(gè)最大池化層,從而達(dá)到提取特征的目的。最后我們使用了三個(gè)全連接層來進(jìn)行預(yù)測(cè)并進(jìn)行輸出。
4. 小結(jié)
這節(jié)課之中我們學(xué)習(xí)了什么是卷積神經(jīng)網(wǎng)絡(luò),同時(shí)我們有具體的學(xué)習(xí)了什么是卷積層以及什么是池化層。于此同時(shí)我們對(duì)于其兩著在 TensorFlow 之中的具體使用進(jìn)行了詳細(xì)的說明,最后我們實(shí)現(xiàn)了一個(gè)卷積神經(jīng)網(wǎng)絡(luò),可以用于圖像分類處理。