深入淺出機器學習CIFAR實戰

CIFAR是另外一種數據集,包含了如下10中數據。

本次實驗採用VGG網絡模型,精度非常高,resnet殘差網絡模型沒有測試成功,在擬合時候一直不收斂

加載數據集

(x,y), (x_test, y_test) = datasets.cifar10.load_data()

剔除標籤多餘維度

y = tf.squeeze(y, axis=1)   #tf.Tensor([6 9 9 ... 9 1 1]
y_test = tf.squeeze(y_test, axis=1)

構建Dataset數據集,打散,數據歸一化,類型轉換,batch處理

train_db = tf.data.Dataset.from_tensor_slices((x,y))
train_db = train_db.shuffle(1000).map(preprocess).batch(128)

test_db = tf.data.Dataset.from_tensor_slices((x_test,y_test))
test_db = test_db.map(preprocess).batch(64)
def preprocess(x, y):
    # [0~1]
    x = 2*tf.cast(x, dtype=tf.float32) / 255.-1
    y = tf.cast(y, dtype=tf.int32)
    return x,y

卷積層模型

conv_layers = [ # 5 units of conv + max pooling
    # unit 1
    layers.Conv2D(64, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(64, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 2
    layers.Conv2D(128, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(128, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 3
    layers.Conv2D(256, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(256, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 4
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 5
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same')
]

全鏈接層模型

conv_net = Sequential(conv_layers)
conv_net.add(layers.Flatten())
conv_net.add(tf.keras.layers.Dense(256, activation=tf.nn.relu)) #隱藏層
conv_net.add(tf.keras.layers.Dense(128, activation=tf.nn.relu))
conv_net.add(tf.keras.layers.Dense(10,   activation='softmax')) #輸出層 tf.nn.softmax

編譯

conv_net.compile(optimizer='adam',
                       loss='sparse_categorical_crossentropy',
                       metrics=['accuracy'])

擬合

conv_net.fit(train_db, epochs=100)

估值

val_loss, val_acc = conv_net.evaluate(test_db)  # 測試集,損失值,準確度返回
print(val_loss)
print(val_acc)

模型保存

conv_net.save('model_vgg_cifar.h5')

 

預測圖片如下:

 

加載模型

model = tf.keras.models.load_model('model_vgg_cifar.h5')

處理圖片爲32*32

(filepath,filename) = os.path.split(path)

img = cv2.imread(path)
img = cv2.resize(img, (32, 32))
path = filepath+'/32_32/'+filename
cv2.imwrite(path,img)
print(path)

轉換維度和類型

img = np.reshape(img,(1,32,32,3))
img = img.astype(float32)

歸一化到-1~1

img = 2 * tf.cast(img, dtype=tf.float32) / 255. - 1

預測

predictions = model.predict(img)
print(predictions)
index = np.argmax(predictions[0])
print(index,NumToEcode(index))
def NumToEcode(num):
    list = ["airplan","car","bird","cat","deer","dog","frog","horse","ship","truck"]

    return list[num]

實驗結果如下:

完整代碼如下:

import  tensorflow as tf
from    tensorflow.keras import layers, optimizers, datasets, Sequential
import  os
import sys
import cv2
import numpy as np
import matplotlib.pyplot as plt
from numpy import float32,float64
os.environ['TF_CPP_MIN_LOG_LEVEL']='2'
tf.random.set_seed(2345)

conv_layers = [ # 5 units of conv + max pooling
    # unit 1
    layers.Conv2D(64, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(64, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 2
    layers.Conv2D(128, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(128, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 3
    layers.Conv2D(256, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(256, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 4
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same'),

    # unit 5
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.Conv2D(512, kernel_size=[3, 3], padding="same", activation=tf.nn.relu),
    layers.MaxPool2D(pool_size=[2, 2], strides=2, padding='same')
]



def preprocess(x, y):
    # [0~1]
    x = 2*tf.cast(x, dtype=tf.float32) / 255.-1
    y = tf.cast(y, dtype=tf.int32)
    return x,y

def show(img):
    cv2.imshow("pWinName", img)
    cv2.waitKey(0)

#裝載圖像矩陣數據
(x,y), (x_test, y_test) = datasets.cifar10.load_data() #(50000, 32, 32, 3) (50000, 1) (10000, 32, 32, 3) (10000, 1)

y = tf.squeeze(y, axis=1)   #tf.Tensor([6 9 9 ... 9 1 1]
y_test = tf.squeeze(y_test, axis=1)

print(x.shape, y.shape, x_test.shape, y_test.shape)

train_db = tf.data.Dataset.from_tensor_slices((x,y))
train_db = train_db.shuffle(1000).map(preprocess).batch(128)

test_db = tf.data.Dataset.from_tensor_slices((x_test,y_test))
test_db = test_db.map(preprocess).batch(64)

sample = next(iter(train_db))
print('sample:', sample[0].shape, sample[1].shape,tf.reduce_min(sample[0]), tf.reduce_max(sample[0]))

def training():
    # [b, 32, 32, 3] => [b, 1, 1, 512]
    conv_net = Sequential(conv_layers)
    conv_net.add(layers.Flatten())
    conv_net.add(tf.keras.layers.Dense(256, activation=tf.nn.relu)) #隱藏層
    conv_net.add(tf.keras.layers.Dense(128, activation=tf.nn.relu))
    conv_net.add(tf.keras.layers.Dense(10,   activation='softmax')) #輸出層 tf.nn.softmax

    conv_net.compile(optimizer='adam',
                           loss='sparse_categorical_crossentropy',
                           metrics=['accuracy'])

    #conv_net.build(input_shape=(128, 32, 32, 3))
    #conv_net.summary()

    conv_net.fit(train_db, epochs=100)
    val_loss, val_acc = conv_net.evaluate(test_db)  # 測試集,損失值,準確度返回
    print(val_loss)
    print(val_acc)

    conv_net.save('model_vgg_cifar.h5')

def NumToEcode(num):
    list = ["airplan","car","bird","cat","deer","dog","frog","horse","ship","truck"]

    return list[num]

def  predicted(path):
    model = tf.keras.models.load_model('model_vgg_cifar.h5')
    (filepath,filename) = os.path.split(path)

    img = cv2.imread(path)
    img = cv2.resize(img, (32, 32))
    path = filepath+'/32_32/'+filename
    cv2.imwrite(path,img)
    print(path)

    img = np.reshape(img,(1,32,32,3))
    img = img.astype(float32)

    img = 2 * tf.cast(img, dtype=tf.float32) / 255. - 1

    predictions = model.predict(img)
    print(predictions)
    index = np.argmax(predictions[0])
    print(index,NumToEcode(index))

if __name__ == '__main__':

    #training()
    predicted("./bmp_cifar/airplan.jpg")

發佈了403 篇原創文章 · 獲贊 1369 · 訪問量 530萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章