{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.7.10","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"},"kaggle":{"accelerator":"gpu","dataSources":[{"sourceId":3362,"databundleVersionId":31148,"sourceType":"competition"},{"sourceId":28903,"sourceType":"datasetVersion","datasetId":22535},{"sourceId":30378,"sourceType":"datasetVersion","datasetId":23777}],"dockerImageVersionId":30146,"isInternetEnabled":true,"language":"python","sourceType":"notebook","isGpuEnabled":true}},"nbformat_minor":4,"nbformat":4,"cells":[{"cell_type":"code","source":"import pandas as pd\nimport numpy as np\nimport seaborn as sns\nimport matplotlib.pyplot as plt\nimport os\nimport random\nimport zipfile\nfrom sklearn.model_selection import train_test_split\nfrom sklearn.metrics import ConfusionMatrixDisplay, confusion_matrix, classification_report \nimport tensorflow as tf\nfrom keras.preprocessing.image import load_img, ImageDataGenerator\nfrom keras.models import Sequential, Model\nfrom keras.layers import Conv2D, MaxPool2D, Flatten, Dense, GlobalAveragePooling2D, Dropout, BatchNormalization, Input\nfrom keras.callbacks import ReduceLROnPlateau, EarlyStopping, ModelCheckpoint\nfrom keras.applications.vgg16 import VGG16, preprocess_input\n\nbatch_size = 128","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","_kg_hide-input":true,"execution":{"iopub.status.busy":"2024-03-20T20:11:11.591198Z","iopub.execute_input":"2024-03-20T20:11:11.59159Z","iopub.status.idle":"2024-03-20T20:11:17.700035Z","shell.execute_reply.started":"2024-03-20T20:11:11.591484Z","shell.execute_reply":"2024-03-20T20:11:17.699327Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"seed = 666\ntf.random.set_seed(seed)\nnp.random.seed(seed)\nos.environ[\"PYTHONHASHSEED\"] = str(seed)                      \nrandom.seed(666)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:26:35.604435Z","iopub.execute_input":"2024-03-20T20:26:35.604835Z","iopub.status.idle":"2024-03-20T20:26:35.609886Z","shell.execute_reply.started":"2024-03-20T20:26:35.604799Z","shell.execute_reply":"2024-03-20T20:26:35.609015Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"[take me to the top](#section-top)","metadata":{}},{"cell_type":"markdown","source":"<a id=\"section-one\"></a>\n\n# 1) Unzip Datasets","metadata":{}},{"cell_type":"code","source":"os.listdir(\"../input/dogs-vs-cats/\")","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:26:39.283417Z","iopub.execute_input":"2024-03-20T20:26:39.283989Z","iopub.status.idle":"2024-03-20T20:26:39.298337Z","shell.execute_reply.started":"2024-03-20T20:26:39.283954Z","shell.execute_reply":"2024-03-20T20:26:39.297191Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"TRAIN_PATH = \"../input/dogs-vs-cats/train.zip\"\nTEST_PATH = \"../input/dogs-vs-cats/test1.zip\"\n\nFILES = \"/kaggle/files/unzipped/\"\n\nwith zipfile.ZipFile(TRAIN_PATH, 'r') as zipp:\n    zipp.extractall(FILES)\n    \nwith zipfile.ZipFile(TEST_PATH, 'r') as zipp:\n    zipp.extractall(FILES)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:26:41.317556Z","iopub.execute_input":"2024-03-20T20:26:41.318347Z","iopub.status.idle":"2024-03-20T20:26:58.051083Z","shell.execute_reply.started":"2024-03-20T20:26:41.318307Z","shell.execute_reply":"2024-03-20T20:26:58.05029Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_df = pd.DataFrame({\"file\": os.listdir(\"/kaggle/files/unzipped/train\")})\ntrain_df[\"label\"] = train_df[\"file\"].apply(lambda x: x.split(\".\")[0])\n\ntrain_df","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:26:58.05277Z","iopub.execute_input":"2024-03-20T20:26:58.053029Z","iopub.status.idle":"2024-03-20T20:26:58.102482Z","shell.execute_reply.started":"2024-03-20T20:26:58.052997Z","shell.execute_reply":"2024-03-20T20:26:58.101524Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"test_df = pd.DataFrame({\"file\": os.listdir(\"/kaggle/files/unzipped/test1\")})\n\ntest_df.head()","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:26:58.104213Z","iopub.execute_input":"2024-03-20T20:26:58.104552Z","iopub.status.idle":"2024-03-20T20:26:58.209356Z","shell.execute_reply.started":"2024-03-20T20:26:58.104503Z","shell.execute_reply":"2024-03-20T20:26:58.208486Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"[take me to the top](#section-top)","metadata":{}},{"cell_type":"markdown","source":"<a id=\"section-four\"></a>\n\n# 4) Data Preparation & Augmentation","metadata":{}},{"cell_type":"code","source":"train_data, val_data = train_test_split(train_df, \n                                        test_size = 0.2, \n                                        stratify = train_df[\"label\"], \n                                        random_state = 666)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:27:07.654881Z","iopub.execute_input":"2024-03-20T20:27:07.655182Z","iopub.status.idle":"2024-03-20T20:27:07.716087Z","shell.execute_reply.started":"2024-03-20T20:27:07.655148Z","shell.execute_reply":"2024-03-20T20:27:07.71525Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from keras.applications.vgg16 import VGG16\nvggmodel = VGG16(weights='imagenet', include_top=True)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:37:09.584217Z","iopub.execute_input":"2024-03-20T20:37:09.584909Z","iopub.status.idle":"2024-03-20T20:37:11.523287Z","shell.execute_reply.started":"2024-03-20T20:37:09.584868Z","shell.execute_reply":"2024-03-20T20:37:11.522539Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"for layers in (vggmodel.layers)[:19]:\n    print(layers)\n    layers.trainable = True","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:37:26.511885Z","iopub.execute_input":"2024-03-20T20:37:26.512163Z","iopub.status.idle":"2024-03-20T20:37:26.520963Z","shell.execute_reply.started":"2024-03-20T20:37:26.512133Z","shell.execute_reply":"2024-03-20T20:37:26.520037Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from keras.layers import Dense\nfrom keras.models import Model\nX= vggmodel.layers[-2].output\n#X = Dense(256, activation ='relu')(X)\npredictions = Dense(1, activation=\"sigmoid\")(X)\nmodel_final = Model(vggmodel.input,predictions)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:37:47.893162Z","iopub.execute_input":"2024-03-20T20:37:47.893859Z","iopub.status.idle":"2024-03-20T20:37:47.911778Z","shell.execute_reply.started":"2024-03-20T20:37:47.893824Z","shell.execute_reply":"2024-03-20T20:37:47.911107Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from keras import optimizers\n\nmodel_final.compile(loss=\"binary_crossentropy\", optimizer=tf.keras.optimizers.SGD (lr=0.00001, momentum=0), metrics=[\"accuracy\"])\n\nmodel_final.summary()","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:40:16.876587Z","iopub.execute_input":"2024-03-20T20:40:16.877534Z","iopub.status.idle":"2024-03-20T20:40:16.901594Z","shell.execute_reply.started":"2024-03-20T20:40:16.877494Z","shell.execute_reply":"2024-03-20T20:40:16.899952Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from tensorflow.keras.callbacks import ModelCheckpoint, EarlyStopping\nimport tensorflow as tf\n#checkpoint = ModelCheckpoint(\"vgg16_50.h5\", monitor='val_accuracy', verbose=1, save_best_only=True, save_weights_only=False, mode='auto', period=1)\n#early = EarlyStopping(monitor='val_accuracy', min_delta=0, patience=10, verbose=1, mode='auto')\nhistory=model_final.fit_generator(generator= train_generator,\n                            steps_per_epoch= (number_of_trainsamples/batch),\n                            epochs= 200,\n                            validation_data= val_generator,\n                            validation_steps=(number_of_testsamples/batch))","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"<a id=\"section-four1\"></a>\n\n## Sample Augmentation","metadata":{}},{"cell_type":"code","source":"datagen = ImageDataGenerator(\n    rotation_range = 30, \n    width_shift_range = 0.1,\n    height_shift_range = 0.1, \n    brightness_range = (0.5, 1), \n    zoom_range = 0.2,\n    horizontal_flip = True, \n    rescale = 1./255,\n)\n\nsample_df = train_data.sample(1)\n\nsample_generator = datagen.flow_from_dataframe(\n    dataframe = sample_df,\n    directory = FILES + \"train/\",\n    x_col = \"file\",\n    y_col = \"label\",\n    class_mode = \"categorical\",\n    target_size = (224, 224),\n    seed = 666\n)","metadata":{"_kg_hide-input":true,"execution":{"iopub.status.busy":"2024-03-20T20:41:26.591548Z","iopub.execute_input":"2024-03-20T20:41:26.592107Z","iopub.status.idle":"2024-03-20T20:41:26.605191Z","shell.execute_reply.started":"2024-03-20T20:41:26.592066Z","shell.execute_reply":"2024-03-20T20:41:26.604248Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_datagen = ImageDataGenerator(\n    rotation_range = 15, \n#     width_shift_range = 0.1,\n#     height_shift_range = 0.1, \n#     brightness_range = (0.5, 1), \n#     zoom_range = 0.1,\n    horizontal_flip = True,\n    preprocessing_function = preprocess_input\n)\n\nval_datagen = ImageDataGenerator(preprocessing_function = preprocess_input)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:41:34.628108Z","iopub.execute_input":"2024-03-20T20:41:34.628697Z","iopub.status.idle":"2024-03-20T20:41:34.633635Z","shell.execute_reply.started":"2024-03-20T20:41:34.62866Z","shell.execute_reply":"2024-03-20T20:41:34.632646Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_generator = train_datagen.flow_from_dataframe(\n    dataframe = train_data,\n    directory = FILES + \"train/\",\n    x_col = \"file\",\n    y_col = \"label\",\n    class_mode = \"categorical\",\n    target_size = (224, 224),\n    batch_size = batch_size,\n    seed = 666,\n)\n\nval_generator = val_datagen.flow_from_dataframe(\n    dataframe = val_data,\n    directory = FILES + \"train/\",\n    x_col = \"file\",\n    y_col = \"label\",\n    class_mode = \"categorical\",\n    target_size = (224, 224),\n    batch_size = batch_size,\n    seed = 666,\n    shuffle = False\n)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:41:36.648399Z","iopub.execute_input":"2024-03-20T20:41:36.649076Z","iopub.status.idle":"2024-03-20T20:41:36.987056Z","shell.execute_reply.started":"2024-03-20T20:41:36.64904Z","shell.execute_reply":"2024-03-20T20:41:36.986198Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"from tensorflow.keras.callbacks import ModelCheckpoint, EarlyStopping\nimport tensorflow as tf\n\nhistory=model_final.fit_generator(generator= train_generator,\n                            steps_per_epoch= train_data.shape[0] // batch_size,\n                            epochs= 10,\n                            validation_data= val_generator,\n                            validation_steps=val_data.shape[0] // batch_size)","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:44:53.100505Z","iopub.execute_input":"2024-03-20T20:44:53.101067Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"tf.keras.backend.clear_session()\n\nmodel = vgg16_pretrained()\n\nmodel.load_weights(\"./catdog_vgg16_.10-0.983774.hdf5\")","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:25:54.034101Z","iopub.status.idle":"2024-03-20T20:25:54.034445Z","shell.execute_reply.started":"2024-03-20T20:25:54.034266Z","shell.execute_reply":"2024-03-20T20:25:54.034289Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"val_pred = model.predict(val_generator, steps = np.ceil(val_data.shape[0] / batch_size))\nval_data.loc[:, \"val_pred\"] = np.argmax(val_pred, axis = 1)\n\nlabels = dict((v, k) for k, v in val_generator.class_indices.items())\n\nval_data.loc[:, \"val_pred\"] = val_data.loc[:, \"val_pred\"].map(labels)","metadata":{"_kg_hide-input":false,"_kg_hide-output":true,"execution":{"iopub.status.busy":"2024-03-20T20:25:54.037186Z","iopub.status.idle":"2024-03-20T20:25:54.037571Z","shell.execute_reply.started":"2024-03-20T20:25:54.037357Z","shell.execute_reply":"2024-03-20T20:25:54.037376Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"labels","metadata":{"execution":{"iopub.status.busy":"2024-03-20T20:25:54.03867Z","iopub.status.idle":"2024-03-20T20:25:54.03905Z","shell.execute_reply.started":"2024-03-20T20:25:54.038852Z","shell.execute_reply":"2024-03-20T20:25:54.038872Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"[take me to the top](#section-top)","metadata":{}},{"cell_type":"markdown","source":"<a id=\"section-six2\"></a>\n## Confusion Matrix & Classification Report","metadata":{}},{"cell_type":"code","source":"fig, ax = plt.subplots(figsize = (9, 6))\n\ncm = confusion_matrix(val_data[\"label\"], val_data[\"val_pred\"])\n\ndisp = ConfusionMatrixDisplay(confusion_matrix = cm, display_labels = [\"cat\", \"dog\"])\ndisp.plot(cmap = plt.cm.Blues, ax = ax)\n\nax.set_title(\"Validation Set\")\nplt.show()","metadata":{"_kg_hide-input":true,"execution":{"iopub.status.busy":"2024-03-20T20:25:54.040505Z","iopub.status.idle":"2024-03-20T20:25:54.040965Z","shell.execute_reply.started":"2024-03-20T20:25:54.0407Z","shell.execute_reply":"2024-03-20T20:25:54.04074Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"print(classification_report(val_data[\"label\"], val_data[\"val_pred\"]))","metadata":{"_kg_hide-input":true,"execution":{"iopub.status.busy":"2024-03-20T20:25:54.042595Z","iopub.status.idle":"2024-03-20T20:25:54.043094Z","shell.execute_reply.started":"2024-03-20T20:25:54.042832Z","shell.execute_reply":"2024-03-20T20:25:54.042855Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"<a id=\"section-read\"></a>\n\n# Readings, Resources","metadata":{}},{"cell_type":"markdown","source":"https://towardsdatascience.com/illustrated-10-cnn-architectures-95d78ace614d#c5a6\n\nhttps://keras.io/guides/transfer_learning/\n\nhttps://paperswithcode.com/sota/image-classification-on-imagenet\n\nhttps://viso.ai/deep-learning/vgg-very-deep-convolutional-networks/\n\nhttps://medium.com/mini-distill/effect-of-batch-size-on-training-dynamics-21c14f7a716e\n\nhttps://ai.stackexchange.com/a/4413\n\nhttps://www.kaggle.com/rajmehra03/a-comprehensive-guide-to-transfer-learning\n\nhttps://www.kaggle.com/dansbecker/transfer-learning\n\n\nGood notebooks about this dataset\n\nhttps://www.kaggle.com/uysimty/keras-cnn-dog-or-cat-classification\n\nhttps://www.kaggle.com/bhuvanchennoju/hey-siri-is-it-a-or-class-f1-0-992\n\n\nYou can also look at\n\nhttps://www.kaggle.com/mustafacicek/mnist-cnn-data-augmentation","metadata":{}}]}