{"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":"markdown","source":"# Import libraries and check GPUs","metadata":{}},{"cell_type":"code","source":"import numpy as np\n\nimport os\nos.environ['TF_CPP_MIN_LOG_LEVEL']='2'\n\nimport glob\n\nimport tensorflow as tf\nfrom tensorflow.keras.applications import EfficientNetB3\nfrom tensorflow.keras.models import Sequential\nfrom tensorflow.keras import layers\nAUTOTUNE = tf.data.experimental.AUTOTUNE\ntf.get_logger().setLevel(\"ERROR\")\n\nimport matplotlib.pyplot as plt","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:36.857001Z","iopub.execute_input":"2022-07-20T02:04:36.857915Z","iopub.status.idle":"2022-07-20T02:04:36.865601Z","shell.execute_reply.started":"2022-07-20T02:04:36.857870Z","shell.execute_reply":"2022-07-20T02:04:36.864345Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"print(tf.__version__)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:36.867868Z","iopub.execute_input":"2022-07-20T02:04:36.868618Z","iopub.status.idle":"2022-07-20T02:04:36.884447Z","shell.execute_reply.started":"2022-07-20T02:04:36.868576Z","shell.execute_reply":"2022-07-20T02:04:36.883192Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"device_name = tf.test.gpu_device_name()\nif \"GPU\" not in device_name:\n    print(\"GPU device not found\")\nprint('Found GPU at: {}'.format(device_name))\nprint(\"Num GPUs Available: \", len(tf.config.experimental.list_physical_devices('GPU')))","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:36.887519Z","iopub.execute_input":"2022-07-20T02:04:36.888359Z","iopub.status.idle":"2022-07-20T02:04:36.899885Z","shell.execute_reply.started":"2022-07-20T02:04:36.888317Z","shell.execute_reply":"2022-07-20T02:04:36.898651Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Unzip data","metadata":{}},{"cell_type":"code","source":"import zipfile\n\nzip_df = zipfile.ZipFile(\"/kaggle/input/dogs-vs-cats-redux-kernels-edition/train.zip\", 'r')\nzip_df.extractall(\"/kaggle/working/\")\nzip_df.close()\nzip_df = zipfile.ZipFile(\"/kaggle/input/dogs-vs-cats-redux-kernels-edition/test.zip\", 'r')\nzip_df.extractall(\"/kaggle/working/\")\nzip_df.close()","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:36.901688Z","iopub.execute_input":"2022-07-20T02:04:36.902384Z","iopub.status.idle":"2022-07-20T02:04:53.717343Z","shell.execute_reply.started":"2022-07-20T02:04:36.902343Z","shell.execute_reply":"2022-07-20T02:04:53.716225Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Create dataset and split train validation dataset","metadata":{}},{"cell_type":"code","source":"def get_path(path,name):\n    return glob.glob(path+'/*.'+name)\ndog_check = lambda x: 1 if x.split('.')[1].split('/')[-1] == 'dog' else 0","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:53.721702Z","iopub.execute_input":"2022-07-20T02:04:53.723792Z","iopub.status.idle":"2022-07-20T02:04:53.729077Z","shell.execute_reply.started":"2022-07-20T02:04:53.723758Z","shell.execute_reply":"2022-07-20T02:04:53.727955Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"data_list = get_path('./train','jpg')\nresult = list(map(dog_check,data_list))\n\nprint('train image:',len(data_list))\nprint('dog images:',result.count(1),'cat images:',result.count(0))","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:53.730697Z","iopub.execute_input":"2022-07-20T02:04:53.731179Z","iopub.status.idle":"2022-07-20T02:04:53.833755Z","shell.execute_reply.started":"2022-07-20T02:04:53.731139Z","shell.execute_reply":"2022-07-20T02:04:53.832658Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_data = []\nval_data = []\ntrain_label = []\nval_label = []\n\n#dogs image ratio\nsplit_ratio = 0.9\n\ndogs_list = [i for i in data_list if dog_check(i)]\ncats_list = [i for i in data_list if not dog_check(i)]\n\nfor i in range(int(len(data_list)/2)):\n    if (i < len(data_list)/2*split_ratio):\n        train_data.append(dogs_list[i])\n        train_data.append(cats_list[i])\n    else:\n        val_data.append(dogs_list[i])\n        val_data.append(cats_list[i])\n\ntrain_label = list(map(dog_check,train_data))\nval_label = list(map(dog_check,val_data))","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:53.835145Z","iopub.execute_input":"2022-07-20T02:04:53.835793Z","iopub.status.idle":"2022-07-20T02:04:53.900604Z","shell.execute_reply.started":"2022-07-20T02:04:53.835750Z","shell.execute_reply":"2022-07-20T02:04:53.899631Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"img_size = 300\n\ndef preprocess_image(image):\n  image = tf.image.decode_jpeg(image, channels=3)\n  image = tf.image.resize(image, [img_size, img_size])\n\n  return image\n\ndef load_and_preprocess_image(path):\n  image = tf.io.read_file(path)\n  return preprocess_image(image)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:53.902197Z","iopub.execute_input":"2022-07-20T02:04:53.902594Z","iopub.status.idle":"2022-07-20T02:04:53.908903Z","shell.execute_reply.started":"2022-07-20T02:04:53.902555Z","shell.execute_reply":"2022-07-20T02:04:53.907881Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"ds_train = tf.data.Dataset.from_tensor_slices((train_data,train_label))\nds_val = tf.data.Dataset.from_tensor_slices((val_data,val_label))\n\ndef load_and_preprocess_from_path_label(path, label):\n  return load_and_preprocess_image(path), tf.one_hot(label, 2)\n\nds_train = ds_train.map(load_and_preprocess_from_path_label)\nds_val = ds_val.map(load_and_preprocess_from_path_label)\n\nprint('train dataset:',len(ds_train),'validation dataset:',len(ds_val))","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:53.910525Z","iopub.execute_input":"2022-07-20T02:04:53.911272Z","iopub.status.idle":"2022-07-20T02:04:54.137584Z","shell.execute_reply.started":"2022-07-20T02:04:53.911235Z","shell.execute_reply":"2022-07-20T02:04:54.136526Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Dataset batch processing","metadata":{}},{"cell_type":"code","source":"batch_size = 64\n\nds_train = ds_train.shuffle(buffer_size=2000)#if out of memory,check your buffer and replace value\nds_batch_train = ds_train.batch(batch_size=batch_size, drop_remainder=False)\nds_batch_train = ds_batch_train.prefetch(tf.data.AUTOTUNE)\nds_batch_val = ds_val.batch(batch_size=batch_size, drop_remainder=False)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:54.140205Z","iopub.execute_input":"2022-07-20T02:04:54.140827Z","iopub.status.idle":"2022-07-20T02:04:54.150413Z","shell.execute_reply.started":"2022-07-20T02:04:54.140786Z","shell.execute_reply":"2022-07-20T02:04:54.149463Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Load EfficientNet pretrained model and rebuild model","metadata":{}},{"cell_type":"code","source":"img_augmentation = Sequential(\n    [\n        layers.RandomRotation(factor=0.15),\n        layers.RandomTranslation(height_factor=0.1, width_factor=0.1),\n        layers.RandomFlip(),\n        layers.RandomContrast(factor=0.1),\n    ],\n    name=\"img_augmentation\",\n)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:54.156353Z","iopub.execute_input":"2022-07-20T02:04:54.156616Z","iopub.status.idle":"2022-07-20T02:04:54.174179Z","shell.execute_reply.started":"2022-07-20T02:04:54.156591Z","shell.execute_reply":"2022-07-20T02:04:54.173303Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def build_model(num_classes):\n    \n    model = Sequential()\n    \n    # Image augmentation\n    model.add(layers.Input(shape=(img_size, img_size, 3)))\n    model.add(img_augmentation)\n    \n    #Base pretrained model\n    base_model = EfficientNetB3(include_top=False, weights=\"imagenet\")\n    # Freeze the pretrained weights\n    base_model.trainable = False\n    model.add(base_model)\n    \n    # Rebuild top\n    top_dropout_rate = 0.2\n    model.add(layers.GlobalAveragePooling2D(name=\"avg_pool\"))\n    model.add(layers.BatchNormalization())\n    model.add(layers.Dropout(top_dropout_rate, name=\"top_dropout\"))\n    model.add(layers.Dense(num_classes, activation=\"softmax\", name=\"pred\"))\n    \n    # Compile\n    optimizer = tf.keras.optimizers.Adam(learning_rate=1e-2)\n    model.compile(\n        optimizer=optimizer, loss=\"categorical_crossentropy\", metrics=[\"accuracy\"]\n    )\n    \n    return model","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:54.177414Z","iopub.execute_input":"2022-07-20T02:04:54.177670Z","iopub.status.idle":"2022-07-20T02:04:54.185725Z","shell.execute_reply.started":"2022-07-20T02:04:54.177646Z","shell.execute_reply":"2022-07-20T02:04:54.184523Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"model = build_model(num_classes=2)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:54.187028Z","iopub.execute_input":"2022-07-20T02:04:54.187976Z","iopub.status.idle":"2022-07-20T02:04:57.884061Z","shell.execute_reply.started":"2022-07-20T02:04:54.187939Z","shell.execute_reply":"2022-07-20T02:04:57.883063Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Model summary\nmodel.summary()","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:57.885539Z","iopub.execute_input":"2022-07-20T02:04:57.885881Z","iopub.status.idle":"2022-07-20T02:04:57.911583Z","shell.execute_reply.started":"2022-07-20T02:04:57.885844Z","shell.execute_reply":"2022-07-20T02:04:57.910372Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Transfer learning","metadata":{}},{"cell_type":"code","source":"epochs = 10\nhist = model.fit(ds_batch_train, epochs=epochs, validation_data=ds_batch_val,batch_size=batch_size, shuffle=True, verbose=1)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:04:57.913289Z","iopub.execute_input":"2022-07-20T02:04:57.913641Z","iopub.status.idle":"2022-07-20T02:36:56.201391Z","shell.execute_reply.started":"2022-07-20T02:04:57.913605Z","shell.execute_reply":"2022-07-20T02:36:56.200198Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def plot_hist(hist):\n    fig = plt.figure(figsize=(16,8))\n    \n    ax1 = fig.add_subplot(1,2,1)\n    ax2 = fig.add_subplot(1,2,2)\n    \n    ax1.plot(hist.history[\"accuracy\"])\n    ax1.plot(hist.history[\"val_accuracy\"])\n    ax1.set_title(\"model accuracy\")\n    ax1.set_ylabel(\"accuracy\")\n    ax1.set_xlabel(\"epoch\")\n    \n    ax2.plot(hist.history[\"loss\"])\n    ax2.plot(hist.history[\"val_loss\"])\n    ax2.set_title(\"model_loss\")\n    ax2.set_ylabel(\"loss\")\n    ax2.set_xlabel(\"epoch\")\n    fig.legend([\"train\", \"validation\"], loc=\"upper left\")\n    fig.show()","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:36:56.204154Z","iopub.execute_input":"2022-07-20T02:36:56.209254Z","iopub.status.idle":"2022-07-20T02:36:56.226560Z","shell.execute_reply.started":"2022-07-20T02:36:56.209215Z","shell.execute_reply":"2022-07-20T02:36:56.225626Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"plot_hist(hist)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:36:56.232721Z","iopub.execute_input":"2022-07-20T02:36:56.234339Z","iopub.status.idle":"2022-07-20T02:36:56.682637Z","shell.execute_reply.started":"2022-07-20T02:36:56.234299Z","shell.execute_reply":"2022-07-20T02:36:56.681593Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"# Predict test image","metadata":{}},{"cell_type":"code","source":"test_list = get_path('./test','jpg')\nid_load = lambda x : int(x.split('/')[-1].split('.')[0])\nid_list = list(map(id_load,test_list))","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:36:56.686995Z","iopub.execute_input":"2022-07-20T02:36:56.689336Z","iopub.status.idle":"2022-07-20T02:36:56.781194Z","shell.execute_reply.started":"2022-07-20T02:36:56.689296Z","shell.execute_reply":"2022-07-20T02:36:56.780300Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"ds_test = tf.data.Dataset.from_tensor_slices(test_list)\nds_test = ds_test.map(load_and_preprocess_image)\nds_batch_test = ds_test.batch(batch_size=64, drop_remainder=False)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:36:56.785504Z","iopub.execute_input":"2022-07-20T02:36:56.787771Z","iopub.status.idle":"2022-07-20T02:36:56.873422Z","shell.execute_reply.started":"2022-07-20T02:36:56.787733Z","shell.execute_reply":"2022-07-20T02:36:56.872530Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"result = model.predict(ds_batch_test,batch_size=64,max_queue_size=1,verbose=1)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:36:56.877763Z","iopub.execute_input":"2022-07-20T02:36:56.880379Z","iopub.status.idle":"2022-07-20T02:37:37.518782Z","shell.execute_reply.started":"2022-07-20T02:36:56.880327Z","shell.execute_reply":"2022-07-20T02:37:37.517818Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"import pandas as pd\n\nsubmission = {'id':id_list,'label':list(map(lambda x:x[1],result))} \nsubmission_df=pd.DataFrame(submission)\nsubmission_df.to_csv('submission.csv',index=False)","metadata":{"execution":{"iopub.status.busy":"2022-07-20T02:41:13.775871Z","iopub.execute_input":"2022-07-20T02:41:13.776291Z","iopub.status.idle":"2022-07-20T02:41:13.828529Z","shell.execute_reply.started":"2022-07-20T02:41:13.776257Z","shell.execute_reply":"2022-07-20T02:41:13.827540Z"},"trusted":true},"execution_count":null,"outputs":[]}]}