Skip to content

Instantly share code, notes, and snippets.

@whan0623
Created September 24, 2021 22:42
Show Gist options
  • Save whan0623/9185dfb7faa7773420c0ecc06bba5c60 to your computer and use it in GitHub Desktop.
Save whan0623/9185dfb7faa7773420c0ecc06bba5c60 to your computer and use it in GitHub Desktop.
MNIST_20210922.ipynb
Display the source blob
Display the rendered blob
Raw
{
"nbformat": 4,
"nbformat_minor": 0,
"metadata": {
"colab": {
"name": "MNIST_20210922.ipynb",
"provenance": [],
"authorship_tag": "ABX9TyNtMee31dEMJlQhP5YOQERH",
"include_colab_link": true
},
"kernelspec": {
"name": "python3",
"display_name": "Python 3"
},
"language_info": {
"name": "python"
}
},
"cells": [
{
"cell_type": "markdown",
"metadata": {
"id": "view-in-github",
"colab_type": "text"
},
"source": [
"<a href=\"https://colab.research.google.com/gist/whan0623/9185dfb7faa7773420c0ecc06bba5c60/mnist_20210922.ipynb\" target=\"_parent\"><img src=\"https://colab.research.google.com/assets/colab-badge.svg\" alt=\"Open In Colab\"/></a>"
]
},
{
"cell_type": "markdown",
"metadata": {
"id": "pfaierpHTjnp"
},
"source": [
"# 데이터 준비 #\n",
"- keras에 내장된 MNIST 데이터셋 로딩"
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "BSiepdmOH0ng",
"outputId": "4c112536-2b39-4078-a554-c597cc26736c"
},
"source": [
"import tensorflow as tf\n",
"import numpy as np\n",
"\n",
"print(tf.__version__)"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"2.6.0\n"
]
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "5mmzffAtH-OL",
"outputId": "97b2206a-18ff-41cc-abce-5a2148e92f0b"
},
"source": [
"(x_train, y_train),(x_test, y_test) = tf.keras.datasets.mnist.load_data()\n",
"\n",
"print('shape of x_train:', x_train.shape)\n",
"print('shape of y_train:', y_train.shape)\n",
"print('shape of x_test:', x_test.shape)\n",
"print('shape of y_test:', y_test.shape)\n"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"Downloading data from https://storage.googleapis.com/tensorflow/tf-keras-datasets/mnist.npz\n",
"11493376/11490434 [==============================] - 0s 0us/step\n",
"11501568/11490434 [==============================] - 0s 0us/step\n",
"shape of x_train: (60000, 28, 28)\n",
"shape of y_train: (60000,)\n",
"shape of x_test: (10000, 28, 28)\n",
"shape of y_test: (10000,)\n"
]
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "G0xg_AHXIUQd",
"outputId": "6aa6bdda-eee5-43bc-f79a-e9f750d5a05c"
},
"source": [
"# IPyhton 디스플레이 설정 변경 - 출력할 최대 열의 개수\n",
"print(x_train[0])\n",
"print(y_train[0])"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"[[ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 3 18 18 18 126 136\n",
" 175 26 166 255 247 127 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 30 36 94 154 170 253 253 253 253 253\n",
" 225 172 253 242 195 64 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 49 238 253 253 253 253 253 253 253 253 251\n",
" 93 82 82 56 39 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 18 219 253 253 253 253 253 198 182 247 241\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 80 156 107 253 253 205 11 0 43 154\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 14 1 154 253 90 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 139 253 190 2 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 11 190 253 70 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 35 241 225 160 108 1\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 81 240 253 253 119\n",
" 25 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 45 186 253 253\n",
" 150 27 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 16 93 252\n",
" 253 187 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 249\n",
" 253 249 64 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 46 130 183 253\n",
" 253 207 2 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 39 148 229 253 253 253\n",
" 250 182 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 24 114 221 253 253 253 253 201\n",
" 78 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 23 66 213 253 253 253 253 198 81 2\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 18 171 219 253 253 253 253 195 80 9 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 55 172 226 253 253 253 253 244 133 11 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 136 253 253 253 212 135 132 16 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]\n",
" [ 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0\n",
" 0 0 0 0 0 0 0 0 0 0]]\n",
"5\n"
]
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 265
},
"id": "ykrj1pjhI32z",
"outputId": "672629a0-4008-4fc5-9ed5-48f110883ef5"
},
"source": [
"import matplotlib.pyplot as plt\n",
"plt.imshow(x_train[0])\n",
"plt.show()"
],
"execution_count": null,
"outputs": [
{
"output_type": "display_data",
"data": {
"image/png": "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\n",
"text/plain": [
"<Figure size 432x288 with 1 Axes>"
]
},
"metadata": {
"needs_background": "light"
}
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "u21awuwxJAaT",
"outputId": "5d161c73-db14-4715-99cf-e11c54d74d5c"
},
"source": [
"print(\"old shape:\", x_train.shape, x_test.shape)\n",
"x_train = x_train.reshape((60000, 28 * 28)) / 255.0\n",
"x_test = x_test.reshape((10000, 28 * 28)) / 255.0\n",
"print(\"new shape:\", x_train.shape, x_test.shape)"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"old shape: (60000, 28, 28) (10000, 28, 28)\n",
"new shape: (60000, 784) (10000, 784)\n"
]
}
]
},
{
"cell_type": "markdown",
"metadata": {
"id": "8kPZlvyMT0Og"
},
"source": [
"# 모델 구축(Building the model) #\n",
"- Suquential model 사용"
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "YEKt83oTJaIt",
"outputId": "e5973fa0-5c39-45c5-ce5d-6e8c25ca7564"
},
"source": [
"model = tf.keras.models.Sequential()\n",
"\n",
"# (?, 784) --> (?, 128)\n",
"model.add(tf.keras.layers.Dense(units=128, activation='relu', input_shape=(28*28,)))\n",
"# (?, 128) --> (?, 10)\n",
"model.add(tf.keras.layers.Dense(units=10, activation='softmax'))\n",
"\n",
"model.summary()"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"Model: \"sequential\"\n",
"_________________________________________________________________\n",
"Layer (type) Output Shape Param # \n",
"=================================================================\n",
"dense (Dense) (None, 128) 100480 \n",
"_________________________________________________________________\n",
"dense_1 (Dense) (None, 10) 1290 \n",
"=================================================================\n",
"Total params: 101,770\n",
"Trainable params: 101,770\n",
"Non-trainable params: 0\n",
"_________________________________________________________________\n"
]
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/",
"height": 312
},
"id": "vai-quHFNA2S",
"outputId": "d8437403-b179-4dac-9107-c7f6dbf05dc9"
},
"source": [
"tf.keras.utils.plot_model(model,\n",
" to_file=\"model_plot.png\",\n",
" show_shapes=True)"
],
"execution_count": null,
"outputs": [
{
"output_type": "execute_result",
"data": {
"image/png": "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\n",
"text/plain": [
"<IPython.core.display.Image object>"
]
},
"metadata": {},
"execution_count": 7
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "FvnLoLmwNUC5"
},
"source": [
"model.compile(optimizer=\"sgd\",\n",
" loss=\"sparse_categorical_crossentropy\",\n",
" metrics=['accuracy']\n",
" )"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "aHOy6LVnNmYB",
"outputId": "a3562a07-23f1-4e8c-8892-b57ecd68aee1"
},
"source": [
"# epochs=5 : 전체 데이터를 5회 반복 사용해서 학습\n",
"# verbose=1 : 모델 학습 진행상황 막대를 출력(1:출력(생략가능), 0:slient, 2:one line per epoch)\n",
"# validation_split=0.2 : 검증용 데이터셋으로 20% 할당\n",
"# batch_size=32 : 한번에 데이터 32개씩 batch로 가져다가 학습에 사용\n",
"\n",
"model.fit(x_train, y_train,\n",
" epochs=5,\n",
" verbose=1,\n",
" validation_split=0.2\n",
" )"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"Epoch 1/5\n",
"1500/1500 [==============================] - 4s 2ms/step - loss: 0.7195 - accuracy: 0.8216 - val_loss: 0.3853 - val_accuracy: 0.8965\n",
"Epoch 2/5\n",
"1500/1500 [==============================] - 3s 2ms/step - loss: 0.3673 - accuracy: 0.8994 - val_loss: 0.3131 - val_accuracy: 0.9143\n",
"Epoch 3/5\n",
"1500/1500 [==============================] - 3s 2ms/step - loss: 0.3143 - accuracy: 0.9121 - val_loss: 0.2802 - val_accuracy: 0.9223\n",
"Epoch 4/5\n",
"1500/1500 [==============================] - 3s 2ms/step - loss: 0.2826 - accuracy: 0.9201 - val_loss: 0.2595 - val_accuracy: 0.9288\n",
"Epoch 5/5\n",
"1500/1500 [==============================] - 3s 2ms/step - loss: 0.2593 - accuracy: 0.9268 - val_loss: 0.2394 - val_accuracy: 0.9336\n"
]
},
{
"output_type": "execute_result",
"data": {
"text/plain": [
"<keras.callbacks.History at 0x7ff5d83ae250>"
]
},
"metadata": {},
"execution_count": 9
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "vHiekkRAPu6Q",
"outputId": "0e611ce4-5410-4ad1-ddb5-f16764442b33"
},
"source": [
"model.evaluate(x_test, y_test)"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"313/313 [==============================] - 1s 2ms/step - loss: 0.2407 - accuracy: 0.9329\n"
]
},
{
"output_type": "execute_result",
"data": {
"text/plain": [
"[0.24072693288326263, 0.9329000115394592]"
]
},
"metadata": {},
"execution_count": 10
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "ufQSm7njRZaw",
"outputId": "a6dbf52d-f271-4454-a745-62a6e9c90d5d"
},
"source": [
"preds = model.predict(x_test, batch_size=128)\n",
"preds[0]"
],
"execution_count": null,
"outputs": [
{
"output_type": "execute_result",
"data": {
"text/plain": [
"array([2.1732778e-04, 2.2600763e-07, 6.0670945e-04, 5.0904569e-03,\n",
" 6.3642024e-06, 1.5237508e-04, 6.4676766e-07, 9.9208844e-01,\n",
" 7.2673472e-05, 1.7648163e-03], dtype=float32)"
]
},
"metadata": {},
"execution_count": 11
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "lK0a4rTlRkug",
"outputId": "18d7db7e-084b-4a74-bf0f-2d71cb708feb"
},
"source": [
"np.argmax(preds[0])"
],
"execution_count": null,
"outputs": [
{
"output_type": "execute_result",
"data": {
"text/plain": [
"7"
]
},
"metadata": {},
"execution_count": 12
}
]
},
{
"cell_type": "code",
"metadata": {
"id": "gik1-FzdRvaJ"
},
"source": [
"model.save('mnist_dnn_model.h5')"
],
"execution_count": null,
"outputs": []
},
{
"cell_type": "markdown",
"metadata": {
"id": "MRMOQ9VPR80q"
},
"source": [
"# 저장된 mnist_dnn_model.h5 모델/가중치 파일을 불러오기 #"
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "HKnyaSANR5yh",
"outputId": "a7c12546-42d8-4461-d1c7-a0c532fe88b9"
},
"source": [
"new_model = tf.keras.models.load_model('mnist_dnn_model.h5')\n",
"new_model.summary()"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"Model: \"sequential\"\n",
"_________________________________________________________________\n",
"Layer (type) Output Shape Param # \n",
"=================================================================\n",
"dense (Dense) (None, 128) 100480 \n",
"_________________________________________________________________\n",
"dense_1 (Dense) (None, 10) 1290 \n",
"=================================================================\n",
"Total params: 101,770\n",
"Trainable params: 101,770\n",
"Non-trainable params: 0\n",
"_________________________________________________________________\n"
]
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "VFKGIO2sSRpo",
"outputId": "fe27fef2-bd36-4316-c640-ac2f0cfd1c20"
},
"source": [
"new_model.evaluate(x_test, y_test)"
],
"execution_count": null,
"outputs": [
{
"output_type": "stream",
"name": "stdout",
"text": [
"313/313 [==============================] - 1s 1ms/step - loss: 0.2407 - accuracy: 0.9329\n"
]
},
{
"output_type": "execute_result",
"data": {
"text/plain": [
"[0.24072693288326263, 0.9329000115394592]"
]
},
"metadata": {},
"execution_count": 15
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "QrRddmDDS-gR",
"outputId": "5018ec24-684b-4fd9-99be-5e1298963cb7"
},
"source": [
"new_preds = new_model.predict(x_test, batch_size=128)\n",
"new_preds[0]"
],
"execution_count": null,
"outputs": [
{
"output_type": "execute_result",
"data": {
"text/plain": [
"array([2.1732778e-04, 2.2600763e-07, 6.0670945e-04, 5.0904569e-03,\n",
" 6.3642024e-06, 1.5237508e-04, 6.4676766e-07, 9.9208844e-01,\n",
" 7.2673472e-05, 1.7648163e-03], dtype=float32)"
]
},
"metadata": {},
"execution_count": 17
}
]
},
{
"cell_type": "code",
"metadata": {
"colab": {
"base_uri": "https://localhost:8080/"
},
"id": "eufo3xElTEU3",
"outputId": "32cadc7c-f263-4550-ce17-13283c892984"
},
"source": [
"np.argmax(new_preds[0])"
],
"execution_count": null,
"outputs": [
{
"output_type": "execute_result",
"data": {
"text/plain": [
"7"
]
},
"metadata": {},
"execution_count": 18
}
]
},
{
"cell_type": "markdown",
"metadata": {
"id": "Bkgnb_NlSXVS"
},
"source": [
"# 참조 : https://rfriend.tistory.com/553 #"
]
}
]
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment