{"cells":[{"metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"cell_type":"code","source":"# This Python 3 environment comes with many helpful analytics libraries installed\n# It is defined by the kaggle/python Docker image: https://github.com/kaggle/docker-python\n# For example, here's several helpful packages to load\n\nimport numpy as np # linear algebra\nimport pandas as pd # data processing, CSV file I/O (e.g. pd.read_csv)\n\n# Input data files are available in the read-only \"../input/\" directory\n# For example, running this (by clicking run or pressing Shift+Enter) will list all files under the input directory\n\nimport os\n##for dirname, _, filenames in os.walk('/kaggle/input'):\n    #for filename in filenames:\n        #print(os.path.join(dirname, filename))\n\n# You can write up to 5GB to the current directory (/kaggle/working/) that gets preserved as output when you create a version using \"Save & Run All\" \n# You can also write temporary files to /kaggle/temp/, but they won't be saved outside of the current session","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"import tensorflow as tf\nimport matplotlib \n# Import libraries\nimport cv2\nimport keras\nimport numpy as np\nimport matplotlib.pyplot as plt\n# Import Warnings \nimport warnings\nwarnings.filterwarnings('ignore')\nimport pandas as pd\nfrom sklearn.utils import shuffle\nfrom sklearn.model_selection import train_test_split\n#from sklearn.cross_validation import train_test_split\n# Import tensorflow as the backend for Keras\nfrom keras import backend as K\nK.image_data_format()\nfrom keras.utils import np_utils\nfrom keras.models import Sequential\nfrom keras.layers.core import Dense, Dropout, Activation, Flatten\nfrom keras.layers.convolutional import Convolution2D, MaxPooling2D\nfrom keras.optimizers import SGD,RMSprop#,adam\nfrom keras.callbacks import TensorBoard\n# Import required libraries for cnfusion matrix\nfrom sklearn.metrics import classification_report,confusion_matrix\nimport itertools\nfrom sklearn.feature_extraction.text import CountVectorizer\nfrom sklearn.naive_bayes import MultinomialNB\nfrom sklearn.pipeline import Pipeline\nimport PIL\nimport IPython.display as ipd\nimport glob\nimport h5py\nimport plotly.graph_objs as go\nimport plotly.express as px\nfrom PIL import Image\nfrom tempfile import mktemp\nfrom keras.models import load_model\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"# read training data from CSV file / Q. 1.a\nimport os\ntrain_df = pd.read_csv('../input/landmark-recognition-2020/train.csv')\nprint(train_df.shape)\n\nsample_path = r\"/kaggle/input/landmark-recognition-2020/sample_submission.csv\"\n\ndf_test = pd.read_csv(sample_path)\n\ntest_path = r\"/kaggle/input/landmark-recognition-2020/test\"\n\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_df.head()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_df.describe()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_df.columns","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#imports for drawing\nimport seaborn as sns\nimport matplotlib.pyplot as plt\n%matplotlib inline ","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#some statistics on the dataset\nprint(\"Some Statistics of the dataset:\\n\")\nprint(train_df['landmark_id'].describe())\nprint(\"\\nThe median of the data is: \", train_df['landmark_id'].median(axis = 0))","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"landmarks = train_df.groupby('landmark_id',as_index=False)['id'].count()\\\n    .sort_values('id',ascending=False).reset_index(drop=True)\nlandmarks.rename(columns={'id':'count'},inplace=True)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"print('Total Unique Landmarks = number of classes: {}'.format(train_df.landmark_id.nunique()))\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#1.b\n\n\nlandmark = train_df.landmark_id.value_counts()\nlandmark_df = pd.DataFrame({'landmark_id':landmark.index, 'frequency':landmark.values}).head(20)\n\nlandmark_df['landmark_id'] =   landmark_df.landmark_id.apply(lambda x: f'landmark_id_{x}')\n\nfig = px.bar(landmark_df, x=\"frequency\", y=\"landmark_id\",color='landmark_id', orientation='h',\n             hover_data=[\"landmark_id\", \"frequency\"],\n             height=1000,\n             title='Number of images per landmark_id (Top 20 landmark_ids)')\nfig.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"firstcnd = {len(landmarks[landmarks['count']<5])}\nsecondcnd = {len(landmarks[landmarks['count']<10])}\nprint(f\"Number of classes with less than 5 images is \", firstcnd)\nprint(f\"Number of classes with less than 10 images is \", secondcnd)\nb = 17297\na = 41637\nc = a - b\nprint(f\"In between:\", c)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"import glob\ntrain_list = glob.glob('../input/landmark-recognition-2020/train/*/*/*/*')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"plt.rcParams[\"axes.grid\"] = False\nf, axarr = plt.subplots(4, 3, figsize=(10, 10))\n\ncurr_row = 0\nfor i in range(12):\n    example = cv2.imread(train_list[i])\n    example = example[:,:,::-1]\n    \n    col = i%4\n    axarr[col, curr_row].imshow(example)\n    if col == 3:\n        curr_row += 1","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"import os\nimport shutil\n\ndtypes = {\n        'id': 'str',\n        'url': 'str',\n        'landmark_id': 'uint32',\n}\ntrain_df = pd.read_csv(\"../input//landmark-recognition-2020/train.csv\", dtype = dtypes)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"'''\nCreate the subfolders with the given labels from the data frame\n'''\ndef create_folders():\n    categories = np.unique(train_df.landmark_id.values)\n    for i in categories:\n        folder = r\"../input/landmark-recognition-2020/train/\" + str(i)\n        if not os.path.exists(folder):\n            print('created folder', i)\n            os.mkdir(folder)\n        else:\n            print( str(i), ' exists!')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"'''\nfunction to move the images to their corresponding folder\n'''\ndef move_files():\n    failed = 0\n    for i, row in train_df.iterrows():\n        filename = r\"../input/landmark-recognition-2020/train/{}/{}.jpg\".format(row.landmark_id, \n                                      row.id )\n        oldfile = r\"../input/landmark-recognition-2020/train/{}.jpg\".format(row.id )\n        if not os.path.exists(filename):\n            try:\n                os.rename(oldfile, filename)\n                print('moved {}.jpg to {}'.format(row.id, row.landmark_id))\n            except:\n                failed +=1\n        else:\n            print('{}.jpg is in {}'.format(row.id, row.landmark_id))\n    \n    print('failed on {} files'.format(failed))","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"from keras.preprocessing.image import ImageDataGenerator\n\ndatagen = ImageDataGenerator(\n        rotation_range=40,\n        width_shift_range=0.2,\n        height_shift_range=0.2,\n        rescale=1./255,\n        shear_range=0.2,\n        zoom_range=0.2,\n        horizontal_flip=True,\n        fill_mode='nearest')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"'''\nfunction to create the training validation folder\n'''\ndef create_test_folder():\n    failed = 0\n    val_size = int(len(train_df)*0.1)\n    val_folder = r\"../input/train_val\"\n    if not os.path.exists(val_folder):\n        os.mkdir(val_folder)\n        \n    for i, row in train_df.iloc[:val_size].iterrows():\n        filename = r\"../input/landmark-recognition-2020/train/{}/{}.jpg\".format(row.landmark_id, \n                                      row.id )\n        newFile = r\"../input/landmark-recognition-2020/train_val/{}/{}.jpg\".format(row.landmark_id, \n                                      row.id )\n        folder = r\"../input/train_val/{}\".format(row.landmark_id )\n        print('testing {}.jpg in {}'.format(row.id, row.landmark_id))\n        if not os.path.exists(newFile):\n            if not os.path.exists(folder):\n                os.mkdir(folder)\n                print('created folder', folder)\n            try:\n                shutil.copy2(filename, newFile)\n                print('copied {}.jpg to train_val/{}'.format(row.id, row.landmark_id))\n            except:\n                failed +=1\n        else:\n            print('{}.jpg is in {}'.format(row.id, row.landmark_id))\n    print('failed on {} files'.format(failed))","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"##defining model \nfrom keras.models import Sequential\nfrom keras.layers import Conv2D, MaxPooling2D\nfrom keras.layers import Activation, Dropout, Flatten, Dense\n\nmodel = Sequential()\nmodel.add(Conv2D(32, (3, 3), input_shape=(150, 150, 3)))\nmodel.add(Activation('relu'))\nmodel.add(MaxPooling2D(pool_size=(2, 2)))\n\nmodel.add(Conv2D(32, (3, 3)))\nmodel.add(Activation('relu'))\nmodel.add(MaxPooling2D(pool_size=(2, 2)))\n\nmodel.add(Conv2D(64, (3, 3)))\nmodel.add(Activation('relu'))\nmodel.add(MaxPooling2D(pool_size=(2, 2)))\n\nmodel.add(Flatten())  # this converts our 3D feature maps to 1D feature vectors\nmodel.add(Dense(64))\nmodel.add(Activation('relu'))\nmodel.add(Dropout(0.5))\nmodel.add(Dense(1))\nmodel.add(Activation('sigmoid'))\n\nmodel.compile(loss='categorical_crossentropy',\n              optimizer='rmsprop',\n              metrics=['categorical_accuracy'])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_df['landmark_id'] = train_df.landmark_id.astype(str)\ntrain_df[\"id\"] = train_df.id.str[0]+\"/\"+train_df.id.str[1]+\"/\"+train_df.id.str[2]+\"/\"+train_df.id+\".jpg\"","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"img_width = img_height = 150 \nval_rate = 0.2\nmin_samples = 20\ntrain_datagen_augmented = ImageDataGenerator(\n        validation_split=val_rate,\n        rotation_range=10,\n        rescale=1. / 255,      \n        shear_range=0.2,       \n        zoom_range=0.2,        \n        horizontal_flip=True)  \n\ndatagen = ImageDataGenerator(rescale=1. / 255)\n# Hyperparameters\nbatch_size = 16\nnb_train_samples = 2000\nnb_validation_samples = 800\nepochs = 10\n# this is the augmentation configuration we will use for training\ntrain_datagen = ImageDataGenerator(\n        rescale=1./255,\n        shear_range=0.2,\n        zoom_range=0.2,\n        horizontal_flip=True)\n\ntrain_generator = train_datagen_augmented.flow_from_dataframe(\n    train_df,\n    directory=\"/kaggle/input/landmark-recognition-2020/train/\",\n    x_col=\"id\",\n    y_col=\"landmark_id\",\n    weight_col=None,\n    target_size=(img_width, img_height),\n    color_mode=\"rgb\",\n    classes=None,\n    class_mode=\"categorical\",\n    batch_size=batch_size,\n    shuffle=True,\n    subset=\"training\",\n    interpolation=\"nearest\",\n    validate_filenames=False)\n\nvalidation_generator = train_datagen_augmented.flow_from_dataframe(\n    train_df,\n    directory=\"/kaggle/input/landmark-recognition-2020/train/\",\n    x_col=\"id\",\n    y_col=\"landmark_id\",\n    weight_col=None,\n    target_size=(img_width, img_height),\n    color_mode=\"rgb\",\n    classes=None,\n    class_mode=\"categorical\",\n    batch_size=batch_size,\n    shuffle=True,\n    subset=\"validation\",\n    interpolation=\"nearest\",\n    validate_filenames=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"model.fit_generator(\n        train_generator,\n        steps_per_epoch=2000 // batch_size,\n        epochs=10,\n        validation_data=validation_generator,\n        validation_steps=800 // batch_size)\nmodel.save_weights('first_try.h5')  # always save your weights after training or during training","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"print(\"Evaluate on test data\")\n\nscore = model.evaluate_generator(validation_generator)\nprint (score)\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"submission = pd.read_csv(\"/kaggle/input/landmark-recognition-2020/sample_submission.csv\")\nsubmission[\"id\"] = submission.id.str[0]+\"/\"+submission.id.str[1]+\"/\"+submission.id.str[2]+\"/\"+submission.id+\".jpg\"\n\ntrained_model = load_model(first_try.h5)\ntest_generator = ImageDataGenerator().flow_from_dataframe(\n    submission,\n    directory=\"/kaggle/input/landmark-recognition-2020/test/\",\n    x_col=\"id\",\n    y_col=None,\n    weight_col=None,\n    target_size=(img_width, img_height),\n    color_mode=\"rgb\",\n    classes=None,\n    class_mode=None,\n    batch_size=1,\n    shuffle=False,\n    subset=None,\n    interpolation=\"nearest\",\n    validate_filenames=False)\n\nfilenames = test_generator.filenames\nnb_samples = len(submission)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"predictions = trained_model.predict_generator(test_generator, steps = nb_samples, verbose = 1)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"# Get classes by np.round\ncl = np.round(pred)\n# Get filenames (set shuffle=false in generator is important)\nfilenames=test_generator.filenames","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"# Data frame\nresults=pd.DataFrame({\"file\":filenames,\"pr\":pred[:,0], \"class\":cl[:,0]})","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"### Submission\ndef get_image_from_number(num):\n    fname = df_test.loc[num,\"id\"]\n    fname = fname + \".jpg\"\n    f1 = fname[0]\n    f2 = fname[1]\n    f3 = fname[2]\n    path = os.path.join(f1,f2,f3,fname)\n    im = cv2.imread(os.path.join(test_path,path))\n    return im\n\ndef get_max_class(preds):\n    p = preds\n    confidence = np.max(p)\n    cla = np.argmax(p)\n    label = decode_label(cla.reshape(1,1))[0]\n    \n    return label, np.round(confidence,2)\n    \ntest_samples = len(df_test)\ntest_df = df_test.copy()\n#for sample in range(test_samples):\n  #  img = get_image_from_number(sample)\n    #img = image_reshape(img, (224, 224)).reshape(1, 224, 224, 3)\n    \n  #  result = model.predict(img)\n    \n  #  label, conf = get_max_class(result)\n  #  test_df.at[sample, 'landmark'] = str(label) + \" \" + str(conf)\n  #  print(label, conf)\n\ntest_df.to_csv(\"submission.csv\", index = False, header = True)\n","execution_count":null,"outputs":[]}],"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":4,"nbformat_minor":4}