Классификация Softmax DNN реализует распознавание изображений жестов

глубокое обучение

1. Набор данных

Набор данных использует изображения для распознавания жестов с шестью различными метками от 0 до 5.портал

2. Принципы и методы

  • Глубокая нейронная сеть DNN, обученная на наборе данных
  • Softmax реализует мультиклассификацию и принимает позицию максимального значения в качестве прогнозируемой метки.
  • Горячее кодирование One-hot для реализации векторного отображения меток 0-5

Три, тюнинг-библиотека

import tensorflow as tf
import numpy as np
import tf_utils
import matplotlib.pyplot as plt
from tensorflow.python.framework import ops #用于tf.get_variable重新运行而不覆盖变量

4. Обработка набора данных

(1) Просмотр изображения

train_x, train_y, test_x, test_y, classes = tf_utils.load_dataset()
index = 5
plt.imshow(train_x[index])
print("y =", np.squeeze(train_y[: ,index]))
print("train_x.shape:", train_x.shape)

在这里插入图片描述

(2) Уменьшение размерности растяжения

# 降维
train_x_flatten = train_x.reshape(train_x.shape[0], -1).T
test_x_flatten = test_x.reshape(test_x.shape[0], -1).T
print("train_x_flatten.shape:", train_x_flatten.shape)
train_x_flatten.shape: (12288, 1080)

(3) Нормализация

# 归一化
train_x1 = train_x_flatten / 255
test_x1 = test_x_flatten / 255

(4) Однократное кодирование тегов

# 标签独热编码
train_y1 = tf_utils.convert_to_one_hot(train_y, 6)
test_y1 = tf_utils.convert_to_one_hot(test_y, 6)

(5) Просмотр обзора данных

print("训练集样本数:", train_x1.shape[1])
print("测试集样本数:", test_x1.shape[1])
print("训练集图像:", train_x1.shape)
print("训练集标签:", train_y1.shape)
print("测试集图像:", test_x1.shape)
print("测试集标签", test_y1.shape)
训练集样本数: 1080
测试集样本数: 120
训练集图像: (12288, 1080)
训练集标签: (6, 1080)
测试集图像: (12288, 120)
测试集标签 (6, 120)

Пять, каждая функция процесса

# 生成placeholder
def creat_placeholder(n_x, n_y):
    x = tf.placeholder(tf.float32, [n_x, None], name="x")
    y = tf.placeholder(tf.float32, [n_y, None], name="y")
    return x,y

# 初始化参数
def initialize_parameters():
    w1 = tf.get_variable("w1",[25,12288],initializer=tf.contrib.layers.xavier_initializer(seed=1))
    b1 = tf.get_variable("b1",[25,1],initializer=tf.zeros_initializer())
    w2 = tf.get_variable("w2", [12, 25], initializer = tf.contrib.layers.xavier_initializer(seed=1))
    b2 = tf.get_variable("b2", [12, 1], initializer = tf.zeros_initializer())
    w3 = tf.get_variable("w3", [6, 12], initializer = tf.contrib.layers.xavier_initializer(seed=1))
    b3 = tf.get_variable("b3", [6, 1], initializer = tf.zeros_initializer())
#     w1 = tf.Variable(tf.random_normal([25, 12288]))
#     b1 = tf.Variable(tf.zeros([25, 1]))
#     w2 = tf.Variable(tf.random_normal([12, 25]))
#     b2 = tf.Variable(tf.zeros([12, 1]))
#     w3 = tf.Variable(tf.random_normal([6, 12]))
#     b3 = tf.Variable(tf.zeros([6, 1]))
    
    parameters = {
        "w1": w1,
        "b1": b1,
        "w2": w2,
        "b2": b2,
        "w3": w3,
        "b3": b3
    }
    return parameters

# 前向传播
def forward_propagation(X, parameters):
    w1 = parameters["w1"]
    b1 = parameters["b1"]
    w2 = parameters["w2"]
    b2 = parameters["b2"]
    w3 = parameters["w3"]
    b3 = parameters["b3"]
    
    z1 = tf.matmul(w1, X) + b1
    a1 = tf.nn.relu(z1)
    z2 = tf.matmul(w2, a1) + b2
    a2 = tf.nn.relu(z2)
    z3 = tf.matmul(w3, a2) + b3
    #a3 = tf.nn.softmax(z3)
    return z3

# 计算成本值
def compute_cost(z3, Y):
    cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits_v2(logits=tf.transpose(z3), labels=tf.transpose(Y)))
    return cost

6. Построение нейросетевой модели

# DNN模型搭建
def nn_model(train_x, train_y, test_x, test_y, learning_rate=0.0001, num_epoch=2000, minibatch_size=32, print_cost=True, is_plot=True):
    ops.reset_default_graph()
    (n_x, m) = train_x.shape 
    n_y = train_y.shape[0]
    x, y = creat_placeholder(n_x, n_y)
    
    parameters = initialize_parameters()
    z3 = forward_propagation(x, parameters)
    cost = compute_cost(z3, y)
    train = tf.train.AdamOptimizer(learning_rate=learning_rate).minimize(cost)
    init = tf.global_variables_initializer()
    seed = 3
    costs = []
    with tf.Session() as session:
        session.run(init)
        for epoch in range(num_epoch):
            epoch_cost = 0
            seed = seed + 1
            num_minibatch = int(m / minibatch_size)
            minibatches = tf_utils.random_mini_batches(train_x, train_y, minibatch_size, seed)
            
            for minibatch in minibatches:
                (minibatch_x, minibatch_y) = minibatch
                _, minibatch_cost = session.run([train, cost], feed_dict={x:minibatch_x, y:minibatch_y})
                epoch_cost = epoch_cost + minibatch_cost / num_minibatch
            if epoch%5 == 0:
                costs.append(epoch_cost)
                if print_cost and epoch%100 == 0:
                    print("epoch =", epoch, "epoch_cost =", epoch_cost)
        if is_plot:
            plt.plot(np.squeeze(costs))
            plt.title("learning_rate =" + str(learning_rate))
            plt.xlabel("epoch")
            plt.ylabel("cost")
            plt.show()
        parameters = session.run(parameters)
        correct_prediction = tf.equal(tf.argmax(z3), tf.argmax(y))
        accuracy = tf.reduce_mean(tf.cast(correct_prediction, "float"))
        print("训练集准确率:", accuracy.eval({x:train_x, y:train_y}))
        print("测试集准确率:", accuracy.eval({x:test_x, y:test_y}))
        return parameters

7. Подайте набор данных для обучения модели

# 训练模型
parameters = nn_model(train_x1, train_y1, test_x1, test_y1)
epoch = 0 epoch_cost = 1.8915627219460225
epoch = 100 epoch_cost = 1.0814920374841401
epoch = 200 epoch_cost = 0.9045906644878967
epoch = 300 epoch_cost = 0.7937486514900668
epoch = 400 epoch_cost = 0.7092051903406779
epoch = 500 epoch_cost = 0.6288680759343233
epoch = 600 epoch_cost = 0.5487878710934612
epoch = 700 epoch_cost = 0.4825858437653743
epoch = 800 epoch_cost = 0.42227065834132105
epoch = 900 epoch_cost = 0.3695441674102436
epoch = 1000 epoch_cost = 0.31023081188852136
epoch = 1100 epoch_cost = 0.25832218676805496
epoch = 1200 epoch_cost = 0.23583885846715985
epoch = 1300 epoch_cost = 0.1781336689988772
epoch = 1400 epoch_cost = 0.15422452421802463
epoch = 1500 epoch_cost = 0.12832456477212184
epoch = 1600 epoch_cost = 0.10107426119573189
epoch = 1700 epoch_cost = 0.08046883931665708
epoch = 1800 epoch_cost = 0.06646379613966652
epoch = 1900 epoch_cost = 0.05467078682373871

训练集准确率: 0.99722224
测试集准确率: 0.75

在这里插入图片描述

8. Предсказание изображения

(1) Прогнозирование образов тренировочного набора

index = 999

x = tf.placeholder(tf.float32, name="x")
plt.imshow(train_x[index])

image = (train_x[index]).reshape(64*64*3, 1) #把图像拉伸降维成列向量
print(image.shape)

with tf.Session() as session: 
    image_prediction = session.run(forward_propagation(x, parameters), feed_dict={x:image})
    prediction_label = np.squeeze(session.run(tf.argmax(image_prediction))) # argmax取softmax分类后向量最大位置
    print("prediction_label:", prediction_label)
    true_label = np.squeeze(train_y[: ,index])
    print("true_label:", true_label)
    if prediction_label == true_label:
        print("预测结果正确!")
    else:
        print("预测结果错误!")
(12288, 1)
prediction_label: 2
true_label: 2
预测结果正确!

在这里插入图片描述

(2) Предсказать изображение тестового набора

index = 46

x = tf.placeholder(tf.float32, name="x")
plt.imshow(test_x[index])

image = (test_x[index]).reshape(64*64*3, 1)
print(image.shape)

with tf.Session() as session:
    image_prediction = session.run(forward_propagation(x, parameters), feed_dict={x:image})
    prediction_label = np.squeeze(session.run(tf.argmax(image_prediction)))
    print("prediction_label:", prediction_label)
    true_label = np.squeeze(test_y[: ,index])
    print("true_label:", true_label)
    if prediction_label == true_label:
        print("预测结果正确!")
    else:
        print("预测结果错误!")
(12288, 1)
prediction_label: 1
true_label: 2
预测结果错误!

在这里插入图片描述

9. Резюме

  • Разница между tf.get_variable() и tf.Variable(), первая устанавливается, когда такой переменной нет, и наоборот, переменная возвращается напрямую. Однако при повторном запуске нужно использовать ops для обработки без перезаписи, иначе будет сообщено об ошибке.
  • Классификатор Softmax требует несколько единиц вывода, В этом примере требуется шесть единиц вывода, поэтому полученное z3/a3 представляет собой матрицу (6, 1), и argmax можно использовать для получения положения максимального значения, то есть , после однократного кодирования Tag of.
  • xavier_initializer инициализирует w: Чтобы поток информации в сети был лучше, дисперсия выходных данных каждого уровня должна быть как можно более равной.
  • Функция потери tf.nn.softmax_cross_entropy_with_logits ⚠ не поддерживает версию tf2.0, вы можете использовать: tf.nn.softmax_cross_entropy_with_logits_v2
  • tf.nn.softmax_cross_entropy_with_logits_v2(logits=tf.transpose(z3), labels=tf.transpose(Y)) где logits — последний уровень прямого распространения вводаЛинейное выходное значение, метки — это метки после входного одноразового кодирования.
  • параметры = session.run(параметры) не бесполезны, поэтому вы можете сохранить окончательные параметры в сеансе.
  • Мини-партия случайным образом делится в каждом раунде обучения, и указанное случайное начальное число меняется.
  • Результаты обучения можно наблюдать: тренировочный набор работает хорошо, а тестовый набор работает не так хорошо, В тестовом наборе, как в примере на рисунке выше, два пальца 2 очень близко друг к другу, поэтому это очень легко идентифицировать их как 1.
  • _, minibatch_cost = session.run([train, cost], feed_dict={x:minibatch_x, y:minibatch_y}) Этот метод написания может запускать функции train и cost одновременно, и функции две в одной.