我开始学习深度学习,但遇到了问题。我从 Andrew W. Trask 的 Grokking Deep Learning 一书开始我的教育。我目前正在学习第 8 章(创建我自己的 MNIST 网络)。没关系,我做到了。但我想了解如何使用 DL 库,如 keras、tentherflow 等。我找到了tutorial,但它使用不同的网络。我有兴趣用 keras 克隆我的网络。我写了代码,但它不能正常工作,我不知道错误在哪里。所以我需要帮助:)
没有 Keras 的代码
import sys, numpy as np
from tensorflow.keras.datasets import mnist
(x_train, y_train), (x_test, y_test) = mnist.load_data()
images, labels = (x_train[0:1000].reshape(1000, 28*28) / 255, y_train[0:1000])
one_hot_labels = np.zeros((len(labels), 10))
for i, l in enumerate(labels):
one_hot_labels[i][l] = 1
labels = one_hot_labels
test_images = x_test.reshape(len(x_test), 28*28) / 255
test_labels = np.zeros((len(y_test), 10))
for i, l in enumerate(y_test):
test_labels[i][l] = 1
np.random.seed(1)
relu = lambda x: (x>=0) * x
relu2deriv = lambda x: x >= 0
batch_size = 100
alpha, iterations = (0.001, 300)
pixel_per_image, num_labels, hidden_size = (784, 10, 100)
weights_0_1 = 0.2 * np.random.random((pixel_per_image, hidden_size)) - 0.1
weights_1_2 = 0.2 * np.random.random((hidden_size, num_labels)) - 0.1
for j in range(iterations):
error, correct_cnt = (0.0, 0)
for i in range(int(len(images) / batch_size)):
batch_start, batch_end = ((i * batch_size), ((i+1) * batch_size))
layer_0 = images[batch_start:batch_end]
layer_1 = relu(np.dot(layer_0,weights_0_1))
dropout_mask = np.random.randint(2, size=layer_1.shape)
layer_1 *= dropout_mask * 2
layer_2 = np.dot(layer_1,weights_1_2)
error += np.sum((labels[batch_start:batch_end] - layer_2) ** 2)
for k in range(batch_size):
correct_cnt += int(np.argmax(layer_2[k:k+1]) == np.argmax(labels[batch_start+k:batch_start+k+1]))
layer_2_delta = (labels[batch_start:batch_end] - layer_2) / batch_size
layer_1_delta = layer_2_delta.dot(weights_1_2.T) * relu2deriv(layer_1)
layer_1_delta *= dropout_mask
weights_1_2 += alpha * layer_1.T.dot(layer_2_delta)
weights_0_1 += alpha * layer_0.T.dot(layer_1_delta)
sys.stdout.write(f"\r I:{str(j)} Train-Err:{str(error/float(len(images)))[0:5]} Train-Acc:{str(correct_cnt/float(len(images)))}")
error, correct_cnt = (0.0, 0)
print(len(test_images))
for i in range(len(test_images)):
layer_0 = test_images[i:i+1]
layer_1 = relu(np.dot(layer_0,weights_0_1))
layer_2 = np.dot(layer_1,weights_1_2)
error += np.sum((test_labels[i:i+1] - layer_2) ** 2)
correct_cnt += int(np.argmax(layer_2) == np.argmax(test_labels[i:i+1]))
sys.stdout.write(f" Test-Err:{str(error/float(len(test_images)))[0:5]} Test-Acc:{str(correct_cnt/float(len(test_images)))}")
print()
结果:Test-Err:0.428 Test-Acc:0.7992
我的 Keras 代码
import numpy as np
from tensorflow import keras
from tensorflow.keras import layers
from keras.optimizers import RMSprop
(x_train, y_train), (x_test, y_test) = keras.datasets.mnist.load_data()
# Scale images to the [0, 1] range
x_train = x_train[0:1000].reshape(1000, 28*28).astype('float32') / 255
y_train = y_train[0:1000]
x_test = x_test.reshape(len(x_test), 28*28).astype('float32') / 255
print("x_train shape:", x_train.shape)
print(x_train.shape[0], "train samples")
print(x_test.shape[0], "test samples")
# convert class vectors to binary class matrices
y_train = keras.utils.to_categorical(y_train, 10)
y_test = keras.utils.to_categorical(y_test, 10)
model = keras.Sequential()
model.add(layers.Dense(100, input_shape=(784,), activation='relu'))
model.add(layers.Dropout(0.5))
model.add(layers.Dense(10))
model.summary()
batch_size = 100
epochs = 300
model.compile(loss = 'categorical_crossentropy',
optimizer = RMSprop(),
metrics = ['accuracy'])
model.fit(x_train, y_train, batch_size=batch_size, epochs=epochs)
结果:loss:8.0127 - accuracy:0.1140
很奇怪。而且 Keras 代码比我的快很多倍。有点奇怪:)