{ "cells": [ { "cell_type": "markdown", "metadata": { "colab_type": "text", "id": "UncprnB0ymAE" }, "source": [ "Below is code with a link to a happy or sad dataset which contains 80 images, 40 happy and 40 sad. \n", "Create a convolutional neural network that trains to 100% accuracy on these images, which cancels training upon hitting training accuracy of >.999\n", "\n", "Hint -- it will work best with 3 convolutional layers." ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [], "source": [ "import tensorflow as tf\n", "import os\n", "import zipfile\n", "from os import path, getcwd, chdir\n", "\n", "# DO NOT CHANGE THE LINE BELOW. If you are developing in a local\n", "# environment, then grab happy-or-sad.zip from the Coursera Jupyter Notebook\n", "# and place it inside a local folder and edit the path to that location\n", "path = f\"{getcwd()}/../tmp2/happy-or-sad.zip\"\n", "\n", "zip_ref = zipfile.ZipFile(path, 'r')\n", "zip_ref.extractall(\"/tmp/h-or-s\")\n", "zip_ref.close()" ] }, { "cell_type": "code", "execution_count": 16, "metadata": {}, "outputs": [], "source": [ "# GRADED FUNCTION: train_happy_sad_model\n", "def train_happy_sad_model():\n", " # Please write your code only where you are indicated.\n", " # please do not remove # model fitting inline comments.\n", "\n", " DESIRED_ACCURACY = 0.999\n", "\n", " class myCallback(tf.keras.callbacks.Callback):\n", " def on_epoch_end(self, epoch, logs={}):\n", " if logs.get('acc')>DESIRED_ACCURACY:\n", " print(\"Reached 100% accuracy so cancelling training!\")\n", " self.model.stop_training=True\n", "\n", " callbacks = myCallback()\n", " \n", " # This Code Block should Define and Compile the Model. Please assume the images are 150 X 150 in your implementation.\n", " model = tf.keras.models.Sequential([\n", " # First conv layer taking in 150 x 150 image input\n", " tf.keras.layers.Conv2D(16, (3,3), activation='relu', input_shape=(150,150,3)),\n", " tf.keras.layers.MaxPooling2D(2,2),\n", " # Second conv layer\n", " tf.keras.layers.Conv2D(32, (3,3), activation='relu'),\n", " tf.keras.layers.MaxPooling2D(2,2),\n", " # Third conv layer\n", " tf.keras.layers.Conv2D(64, (3,3), activation='relu'),\n", " tf.keras.layers.MaxPooling2D(2,2),\n", " # Flatten results\n", " tf.keras.layers.Flatten(),\n", " # First hidden layer\n", " tf.keras.layers.Dense(512, activation='relu'),\n", " # Output layer\n", " tf.keras.layers.Dense(1, activation='sigmoid')\n", " ])\n", "\n", " from tensorflow.keras.optimizers import RMSprop\n", "\n", " model.compile(loss='binary_crossentropy', # Binary Crossentropy loss function to deal with two categories\n", " optimizer=RMSprop(lr=0.001),\n", " metrics=['acc'])\n", " \n", "\n", " # This code block should create an instance of an ImageDataGenerator called train_datagen \n", " # And a train_generator by calling train_datagen.flow_from_directory\n", "\n", " from tensorflow.keras.preprocessing.image import ImageDataGenerator\n", " \n", " # Rescale by a factor or 255\n", " train_datagen = ImageDataGenerator(rescale=1/255)\n", "\n", " # Please use a target_size of 150 X 150.\n", " train_generator = train_datagen.flow_from_directory(\n", " '/tmp/h-or-s', # Location of our happy/sad images\n", " target_size=(150,150), # resize images to 150 x 150\n", " batch_size=128, \n", " class_mode='binary')\n", " # Expected output: 'Found 80 images belonging to 2 classes'\n", "\n", " # This code block should call model.fit_generator and train for\n", " # a number of epochs.\n", " # model fitting\n", " history = model.fit_generator(\n", " train_generator,\n", " steps_per_epoch=8,\n", " epochs=15,\n", " verbose=1,\n", " callbacks=[callbacks])\n", " # model fitting\n", " return history.history['acc'][-1]" ] }, { "cell_type": "code", "execution_count": 17, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Found 80 images belonging to 2 classes.\n", "Epoch 1/15\n", "8/8 [==============================] - 5s 565ms/step - loss: 2.2942 - acc: 0.5000\n", "Epoch 2/15\n", "8/8 [==============================] - 3s 322ms/step - loss: 0.4900 - acc: 0.7937\n", "Epoch 3/15\n", "8/8 [==============================] - 3s 315ms/step - loss: 0.2577 - acc: 0.9047\n", "Epoch 4/15\n", "8/8 [==============================] - 2s 312ms/step - loss: 0.0923 - acc: 0.9734\n", "Epoch 5/15\n", "8/8 [==============================] - 3s 322ms/step - loss: 0.0560 - acc: 0.9766\n", "Epoch 6/15\n", "7/8 [=========================>....] - ETA: 0s - loss: 0.0178 - acc: 1.0000Reached 100% accuracy so cancelling training!\n", "8/8 [==============================] - 2s 312ms/step - loss: 0.0169 - acc: 1.0000\n" ] }, { "data": { "text/plain": [ "1.0" ] }, "execution_count": 17, "metadata": {}, "output_type": "execute_result" } ], "source": [ "# The Expected output: \"Reached 99.9% accuracy so cancelling training!\"\"\n", "train_happy_sad_model()" ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [] } ], "metadata": { "coursera": { "course_slug": "introduction-tensorflow", "graded_item_id": "1kAlw", "launcher_item_id": "PNLYD" }, "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.6.8" } }, "nbformat": 4, "nbformat_minor": 1 }