{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"pygments_lexer":"ipython3","nbconvert_exporter":"python","version":"3.6.4","file_extension":".py","codemirror_mode":{"name":"ipython","version":3},"name":"python","mimetype":"text/x-python"}},"nbformat_minor":4,"nbformat":4,"cells":[{"cell_type":"code","source":"import matplotlib.pyplot as plt\nimport numpy as np\nimport os\nimport tensorflow as tf\nimport tensorflow.keras.layers as tfl\n\nfrom tensorflow.keras.preprocessing import image_dataset_from_directory\nfrom tensorflow.keras.layers.experimental.preprocessing import RandomFlip, RandomRotation\n","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","execution":{"iopub.status.busy":"2022-03-05T15:07:47.002802Z","iopub.execute_input":"2022-03-05T15:07:47.003218Z","iopub.status.idle":"2022-03-05T15:07:51.888094Z","shell.execute_reply.started":"2022-03-05T15:07:47.003137Z","shell.execute_reply":"2022-03-05T15:07:51.887308Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Load data","metadata":{}},{"cell_type":"code","source":"split=0.2\nbatch_size=100\nimg_size=(224,224)\n\ntrain_dataset = image_dataset_from_directory(\n    '../input/dog-vs-cat-classification/train/train',\n    batch_size=batch_size,\n    image_size=img_size,\n    shuffle=True,\n    seed=42,\n    validation_split=split,\n    subset='training',\n)\nval_dataset = image_dataset_from_directory(\n    '../input/dog-vs-cat-classification/train/train',\n    batch_size=batch_size,\n    image_size=img_size,\n    shuffle=True,\n    seed=42,\n    validation_split=split,\n    subset='validation',\n)","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:07:51.889524Z","iopub.execute_input":"2022-03-05T15:07:51.889778Z","iopub.status.idle":"2022-03-05T15:08:06.806802Z","shell.execute_reply.started":"2022-03-05T15:07:51.889719Z","shell.execute_reply":"2022-03-05T15:08:06.806047Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"class_names = train_dataset.class_names\n\nplt.figure(figsize=(10, 10))\nfor images, labels in train_dataset.take(1):\n    for i in range(9):\n        ax = plt.subplot(3, 3, i + 1)\n        plt.imshow(images[i].numpy().astype(\"uint8\"))\n        plt.title(class_names[labels[i]])\n        plt.axis(\"off\")","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:06.807888Z","iopub.execute_input":"2022-03-05T15:08:06.80887Z","iopub.status.idle":"2022-03-05T15:08:10.743677Z","shell.execute_reply.started":"2022-03-05T15:08:06.808832Z","shell.execute_reply":"2022-03-05T15:08:10.742964Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Create Model","metadata":{}},{"cell_type":"code","source":"preprocess_input = tf.keras.applications.mobilenet_v2.preprocess_input","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:10.745268Z","iopub.execute_input":"2022-03-05T15:08:10.745477Z","iopub.status.idle":"2022-03-05T15:08:10.750254Z","shell.execute_reply.started":"2022-03-05T15:08:10.745449Z","shell.execute_reply":"2022-03-05T15:08:10.749546Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def data_augmenter():\n    '''\n    Create a Sequential model composed of 2 layers\n    Returns:\n        tf.keras.Sequential\n    '''\n    data_augmentation = tf.keras.Sequential()\n    data_augmentation.add(RandomFlip(\"horizontal\"))\n    data_augmentation.add(RandomRotation(0.2))\n\n    return data_augmentation","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:10.752145Z","iopub.execute_input":"2022-03-05T15:08:10.752627Z","iopub.status.idle":"2022-03-05T15:08:10.758322Z","shell.execute_reply.started":"2022-03-05T15:08:10.752594Z","shell.execute_reply":"2022-03-05T15:08:10.757569Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"data_augmentation = data_augmenter()","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:10.759649Z","iopub.execute_input":"2022-03-05T15:08:10.760129Z","iopub.status.idle":"2022-03-05T15:08:10.793277Z","shell.execute_reply.started":"2022-03-05T15:08:10.760098Z","shell.execute_reply":"2022-03-05T15:08:10.792688Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def create_model(image_shape=img_size, data_augmentation=data_augmenter()):\n    input_shape = image_shape + (3,)\n    \n    base_model = tf.keras.applications.MobileNetV2(input_shape=input_shape,\n                                                   include_top=False, \n                                                   weights='imagenet')\n    \n    # Freeze the base model by making it non trainable\n    base_model.trainable = False\n    \n    # create the input layer (Same as the imageNetv2 input size)\n    inputs = tf.keras.Input(shape=input_shape) \n    \n    # apply data augmentation to the inputs\n    x = data_augmentation(inputs)\n    \n    # data preprocessing using the same weights the model was trained on\n    # Already Done -> preprocess_input = tf.keras.applications.mobilenet_v2.preprocess_input\n    x = preprocess_input(x) \n    \n    # set training to False to avoid keeping track of statistics in the batch norm layer\n    x = base_model(x, training=False) \n    \n    # Add the new Binary classification layers\n    # use global avg pooling to summarize the info in each channel\n    x = tfl.GlobalAveragePooling2D()(x) \n    #include dropout with probability of 0.2 to avoid overfitting\n    x = tfl.Dropout(0.2)(x)\n        \n    # create a prediction layer with one neuron (as a classifier only needs one)\n    prediction_layer = tfl.Dense(2, activation=\"softmax\")\n    \n    \n    outputs = prediction_layer(x) \n    model = tf.keras.Model(inputs, outputs)\n    \n    return model","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:10.794508Z","iopub.execute_input":"2022-03-05T15:08:10.794771Z","iopub.status.idle":"2022-03-05T15:08:10.8089Z","shell.execute_reply.started":"2022-03-05T15:08:10.794717Z","shell.execute_reply":"2022-03-05T15:08:10.808215Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"model = create_model(img_size, data_augmentation)\nmodel.summary()","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:10.811609Z","iopub.execute_input":"2022-03-05T15:08:10.8118Z","iopub.status.idle":"2022-03-05T15:08:12.343169Z","shell.execute_reply.started":"2022-03-05T15:08:10.811778Z","shell.execute_reply":"2022-03-05T15:08:12.34241Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"base_learning_rate = 0.01\nmodel.compile(optimizer=tf.keras.optimizers.Adam(learning_rate=base_learning_rate),\n              loss=\"sparse_categorical_crossentropy\",\n              metrics=['accuracy'])","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:12.344422Z","iopub.execute_input":"2022-03-05T15:08:12.344658Z","iopub.status.idle":"2022-03-05T15:08:12.360035Z","shell.execute_reply.started":"2022-03-05T15:08:12.344624Z","shell.execute_reply":"2022-03-05T15:08:12.359267Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Train Model","metadata":{}},{"cell_type":"code","source":"initial_epochs = 20\nhistory = model.fit(train_dataset, validation_data=val_dataset, epochs=initial_epochs)","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:08:37.868989Z","iopub.execute_input":"2022-03-05T15:08:37.869297Z","iopub.status.idle":"2022-03-05T15:28:13.31713Z","shell.execute_reply.started":"2022-03-05T15:08:37.869266Z","shell.execute_reply":"2022-03-05T15:28:13.316296Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Prediction","metadata":{}},{"cell_type":"code","source":"import os\nimport pandas as pd\ntest_filenames = os.listdir(\"../input/dog-vs-cat-classification/test/test\")\ntest_df = pd.DataFrame({\n    'id': test_filenames\n})\nnb_samples = test_df.shape[0]","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:28:21.979025Z","iopub.execute_input":"2022-03-05T15:28:21.979281Z","iopub.status.idle":"2022-03-05T15:28:22.190161Z","shell.execute_reply.started":"2022-03-05T15:28:21.979254Z","shell.execute_reply":"2022-03-05T15:28:22.189434Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from keras.preprocessing.image import ImageDataGenerator, load_img\ntest_gen = ImageDataGenerator()\ntest_generator = test_gen.flow_from_dataframe(\n    test_df, \n    \"../input/dog-vs-cat-classification/test/test\", \n    x_col='id',\n    y_col=None,\n    class_mode=None,\n    target_size=img_size,\n    batch_size=batch_size,\n    shuffle=False\n)","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:28:24.52151Z","iopub.execute_input":"2022-03-05T15:28:24.521782Z","iopub.status.idle":"2022-03-05T15:28:36.963359Z","shell.execute_reply.started":"2022-03-05T15:28:24.521746Z","shell.execute_reply":"2022-03-05T15:28:36.962577Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"predict = model.predict(test_generator)\ntest_df['labels'] = np.argmax(predict, axis=-1)","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:29:02.446041Z","iopub.execute_input":"2022-03-05T15:29:02.446298Z","iopub.status.idle":"2022-03-05T15:30:07.788886Z","shell.execute_reply.started":"2022-03-05T15:29:02.446271Z","shell.execute_reply":"2022-03-05T15:30:07.788116Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"test_df","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:31:17.901571Z","iopub.execute_input":"2022-03-05T15:31:17.901846Z","iopub.status.idle":"2022-03-05T15:31:17.916958Z","shell.execute_reply.started":"2022-03-05T15:31:17.901817Z","shell.execute_reply":"2022-03-05T15:31:17.916161Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"test_df.set_index('id')\ntest_df.to_csv('submission.csv',index=False)","metadata":{"execution":{"iopub.status.busy":"2022-03-05T15:31:24.611632Z","iopub.execute_input":"2022-03-05T15:31:24.612326Z","iopub.status.idle":"2022-03-05T15:31:24.633328Z","shell.execute_reply.started":"2022-03-05T15:31:24.612292Z","shell.execute_reply":"2022-03-05T15:31:24.632695Z"},"trusted":true},"execution_count":null,"outputs":[]}]}