{"cells":[{"metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true},"cell_type":"code","source":"import keras\nfrom keras.models import Sequential\nfrom keras.layers.core import Dense, Dropout, Activation, Flatten\nfrom keras.layers.convolutional import Convolution2D, MaxPooling2D\nfrom keras.preprocessing.image import ImageDataGenerator\nfrom keras.models import Model\nfrom keras.models import clone_model\nfrom keras.layers import Dense,Conv2D,Flatten,MaxPool2D,Dropout,BatchNormalization, Input\nfrom keras.optimizers import Adam\nfrom keras.callbacks import ReduceLROnPlateau\n\n#for data handaling\nfrom tqdm.auto import tqdm\nimport numpy as np\nimport pandas as pd \n\n#for image processing\nimport cv2\nfrom PIL import Image\nimport matplotlib.pyplot as plt\n\n#for calc accuaracy and spliting the data\nfrom sklearn.metrics import accuracy_score\nfrom sklearn.ensemble import RandomForestClassifier\nfrom sklearn.model_selection import train_test_split\n%matplotlib inline\nPATH='/kaggle/input/bengaliai-cv19/'\nHEIGHT = 137","execution_count":null,"outputs":[]},{"metadata":{"_uuid":"d629ff2d2480ee46fbb7e2d37f6b5fab8052498a","_cell_guid":"79c7e3d0-c299-4dcb-8224-4455121ee9b0","trusted":true},"cell_type":"code","source":"PATH='/kaggle/input/bengaliai-cv19/'\nHEIGHT = 137\nWIDTH = 236\nSIZE = 64\nbatch_size = 256\nepochs = 64","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"def crop_resize_image(image_df):\n    cropped_resized_img={}\n    for i in tqdm(range(len(image_df))):\n        image=image_df.iloc[i].values.reshape(HEIGHT,WIDTH)\n        _, thresh = cv2.threshold(image, 30, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)\n        contours, _ = cv2.findContours(thresh,cv2.RETR_LIST,cv2.CHAIN_APPROX_SIMPLE)[-2:]\n        x_min=[]\n        x_max=[]\n        y_min=[]\n        y_max=[]\n        for cordinate in contours:\n            x,y,w,h=cv2.boundingRect(cordinate)\n            x_min.append(x)\n            x_max.append(x+w)\n            y_min.append(y)\n            y_max.append(y+h)\n        x1=min(x_min)\n        x2=max(x_max)\n        y1=min(y_min)\n        y2=max(y_max)\n        cropped_img=image[y1:y2,x1:x2]\n        resized_img=cv2.resize(cropped_img,(SIZE,SIZE),interpolation=cv2.INTER_AREA)\n        cropped_resized_img[i]=resized_img.reshape(-1)\n    return pd.DataFrame(cropped_resized_img).T","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"inputs= Input(shape=(SIZE,SIZE,1))\nmodel=Conv2D(filters=32,kernel_size=(3,3),padding='SAME',activation='relu',input_shape=(SIZE,SIZE,1))(inputs)\n#model=MaxPool2D(pool_size=(2,2))(model)\n\nmodel=Conv2D(filters=64,kernel_size=(3,3),padding='SAME',activation='relu')(model)\nmodel=MaxPool2D(pool_size=(2,2))(model)\n\nmodel=Conv2D(filters=128,kernel_size=(3,3),padding='SAME',activation='relu')(model)\nmodel=MaxPool2D(pool_size=(2,2))(model)\n\nmodel=Conv2D(filters=128,kernel_size=(3,3),padding='SAME',activation='relu')(model)\nmodel=MaxPool2D(pool_size=(2,2))(model)\n\nmodel=Conv2D(filters=128,kernel_size=(3,3),padding='SAME',activation='relu')(model)\nmodel=MaxPool2D(pool_size=(2,2))(model)\n\nmodel=Dropout(0.3)(model)\nmodel=BatchNormalization(momentum=0.15)(model)\nmodel=Flatten()(model)\nmodel=Dense(1000,activation='relu')(model)\nmodel=Dropout(0.3)(model)\nmodel=Dense(500,activation='relu')(model)\n\nroot=Dense(168,activation='softmax',name='root')(model)\nvowel=Dense(11,activation='softmax',name='vowel')(model)\nconsonant=Dense(7,activation='softmax',name='consonant')(model)\n\nmodel=Model(inputs=inputs,outputs=[root,vowel,consonant])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"model.summary()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"from tensorflow.keras.utils import plot_model\ncnn1model = keras.Model(inputs=inputs, outputs=[root,vowel ,consonant])\n\nplot_model(cnn1model, to_file='mode4.png')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"lr_root=ReduceLROnPlateau(monitor='root_acc',factor=0.9,patience=3,min_lr=0.00001,verbose=1)\nlr_vowel=ReduceLROnPlateau(monitor='vowel_acc',factor=0.9,patience=3,min_lr=0.00001,verbose=1)\nlr_consonant=ReduceLROnPlateau(monitor='consonant_acc',factor=0.9,patience=3,min_lr=0.00001,verbose=1)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"model.compile(optimizer='adam', loss='categorical_crossentropy', metrics=['accuracy'])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"class MultiOutputDataGenerator(keras.preprocessing.image.ImageDataGenerator):\n\n    def flow(self,\n             x,\n             y=None,\n             batch_size=batch_size,\n             shuffle=True,\n             sample_weight=None,\n             seed=None,\n             save_to_dir=None,\n             save_prefix='',\n             save_format='png',\n             subset=None):\n\n        targets = None\n        target_lengths = {}\n        ordered_outputs = []\n        for output, target in y.items():\n            if targets is None:\n                targets = target\n            else:\n                targets = np.concatenate((targets, target), axis=1)\n            target_lengths[output] = target.shape[1]\n            ordered_outputs.append(output)\n            \n        for flowx, flowy in super().flow(x, targets, batch_size=batch_size,shuffle=shuffle):\n            target_dict = {}\n            i = 0\n            for output in ordered_outputs:\n                target_length = target_lengths[output]\n                target_dict[output] = flowy[:, i: i + target_length]\n                i += target_length\n\n            yield flowx, target_dict","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_image=pd.read_parquet(PATH+'train_image_data_3.parquet').drop(['image_id'],axis=1)\ntrain_image_info=pd.read_csv(PATH+'train.csv')\n\nX_train=crop_resize_image(train_image).values.reshape(-1,SIZE,SIZE,1)\nY_train=train_image_info[3*50210:(3+1)*50210]\n\n_, x_test, _, y_test = train_test_split(X_train, Y_train, test_size=0.85, random_state=420)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"y_test_root = pd.get_dummies(y_test['grapheme_root']).values\ny_test_vowel = pd.get_dummies(y_test['vowel_diacritic']).values\ny_test_consonant = pd.get_dummies(y_test['consonant_diacritic']).values\nprint(y_test_root.shape)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"del train_image\ndel X_train\ndel Y_train","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"def appendHist(h1, h2):\n    if h1 == {}:\n        return h2\n    else:\n        dest = {}\n        for key, value in h1.items():\n            dest[key] = value + h2[key]\n        return dest","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"records={}\n\nfor i in range(1,4):\n    train_image=pd.read_parquet(PATH+'train_image_data_'+str(i)+'.parquet').drop(['image_id'],axis=1)\n    \n    y_train=train_image_info[i*50210:(i+1)*50210]\n    x_train=crop_resize_image(train_image).values.reshape(-1,SIZE,SIZE,1)\n    #plt.imshow(train_image.iloc[100].values.reshape(HEIGHT,WIDTH))\n    del train_image\n\n    #plt.imshow(X_train[100])\n    #print(Y_train.iloc[100])\n    #print('splitting about to start')\n\n\n    #print('splitting completed')\n\n    data_generator=MultiOutputDataGenerator(\n        rotation_range=8,\n        width_shift_range=0.08,\n        shear_range=0.3,\n        height_shift_range=0.08,\n        zoom_range=0.08\n    )\n    data_generator.fit(x_train)\n    #print('fitting completed')\n    \n    y_train_root = pd.get_dummies(y_train['grapheme_root']).values\n    y_train_vowel = pd.get_dummies(y_train['vowel_diacritic']).values\n    y_train_consonant = pd.get_dummies(y_train['consonant_diacritic']).values\n    \n    del y_train\n\n\n    #print('learning about to start')\n    result=model.fit_generator(\n        data_generator.flow(\n            x_train,\n            {\n                'root':y_train_root,'vowel':y_train_vowel,'consonant':y_train_consonant\n            },\n            batch_size=batch_size\n        ),\n        epochs=epochs,\n        validation_data=(x_test,[y_test_root,y_test_vowel,y_test_consonant]),\n        steps_per_epoch=y_train_root.shape[0]//batch_size,\n        callbacks=[lr_root,lr_vowel,lr_consonant]\n    )\n    del x_train\n    del y_train_root\n    del y_train_vowel\n    del y_train_consonant\n\n    records=appendHist(records,result.history) ","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"print(records)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"def plot_graph(x,s):\n    plt.figure(figsize=(10,10))\n    plt.plot(x['val_root_'+s])\n    plt.plot(x['val_vowel_'+s])\n    plt.plot(x['val_consonant_'+s])\n    plt.plot(x['root_'+s])\n    plt.plot(x['vowel_'+s])\n    plt.plot(x['consonant_'+s])\n    plt.title('Learning Dataset '+s)\n    plt.ylabel(s)\n    plt.xlabel('epoch')\n    if s=='accuracy':\n        plt.legend(['val_root_'+s,'val_vowel_'+s,'val_consonant_'+s,'root_'+s,'vowel_'+s,'consonant_'+s], loc='best')\n    elif s=='loss':\n        plt.plot(x['val_'+s])\n        plt.plot(x[s])\n        plt.legend(['val_root_'+s,'val_vowel_'+s,'val_consonant_'+s,'root_'+s,'vowel_'+s,'consonant_'+s,'val_'+s,s], loc='best')\n    plt.show()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"plot_graph(records,'accuracy')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"plot_graph(records,'loss')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"preds_dict = {\n    'grapheme_root': [],\n    'vowel_diacritic': [],\n    'consonant_diacritic': []\n}","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"row_id=[]\ntarget=[]\nfor i in range(4):\n    test_image=pd.read_parquet(PATH+'test_image_data_'+str(i)+'.parquet')\n    test_image.set_index('image_id',inplace=True)\n    x_test=crop_resize_image(test_image).values.reshape(-1,SIZE,SIZE,1)\n    preds = model.predict(x_test)\n    \n    for j, p in enumerate(preds_dict):\n        preds_dict[p] = np.argmax(preds[j], axis=1)\n    \n    for k,id in enumerate(test_image.index.values):\n        row_id+=[id+'_grapheme_root',id+'_vowel_diacritic',id+'_consonant_diacritic']\n        target+=[preds_dict['grapheme_root'][k],preds_dict['vowel_diacritic'][k],preds_dict['consonant_diacritic'][k]]\n\nsubmission = pd.DataFrame({'row_id': row_id, 'target': target})\nsubmission.to_csv('submission.csv', index=False)\nprint(submission)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"temp = {\n    'grapheme_root': [],\n    'vowel_diacritic': [],\n    'consonant_diacritic': []\n}\npreds_dict = {}\npreds_dict['grapheme_root']=[]\npreds_dict['consonant_diacritic']=[]\npreds_dict['vowel_diacritic']=[]","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"y_test=pd.read_csv(PATH+'test.csv')\nfor i in range(4):\n    test_image=pd.read_parquet(PATH+'test_image_data_'+str(i)+'.parquet')\n    test_image.set_index('image_id',inplace=True)\n    x_test=crop_resize_image(test_image).values.reshape(-1,SIZE,SIZE,1)\n    preds = model.predict(x_test)\n    for j, p in enumerate(temp):\n        temp[p] = np.argmax(preds[j], axis=1)\n    preds_dict['grapheme_root'].extend(temp['grapheme_root'])\n    preds_dict['vowel_diacritic'].extend(temp['vowel_diacritic'])\n    preds_dict['consonant_diacritic'].extend(temp['consonant_diacritic'])\n    #print(len(preds_dict['grapheme_root']))","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"root_acc=accuracy_score(y_test['grapheme_root'],preds_dict['grapheme_root'])\nvowel_acc=accuracy_score(y_test['vowel_diacritic'],preds_dict['vowel_diacritic'])\nconsonant_acc=accuracy_score(y_test['consonant_diacritic'],preds_dict['consonant_diacritic'])\n\nprint('Grapheme Roots accuracy: ',root_acc)\nprint('Vowel Diacritic accuracy: ',vowel_acc)\nprint('consonant Diacritic accuracy: ',consonant_acc)\n\nacc=[root_acc,vowel_acc,consonant_acc]\nscore=np.average(acc,weights=[2,1,1])\nprint('Score: ',score)","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}