{"cells":[{"metadata":{"trusted":true},"cell_type":"code","source":"# libraries\nimport numpy as np\nimport pandas as pd\nimport os\nimport cv2\nimport matplotlib.pyplot as plt\n%matplotlib inline\n\nfrom sklearn.model_selection import train_test_split\nfrom sklearn.metrics import roc_auc_score\nimport torch\nfrom torch.utils.data import TensorDataset, DataLoader,Dataset\nimport torch.nn as nn\nimport torch.nn.functional as F\nimport torchvision\nimport torchvision.transforms as transforms\nimport torch.optim as optim\nfrom torch.optim import lr_scheduler\nimport time \nimport tqdm\nfrom PIL import Image\ntrain_on_gpu = True\nfrom torch.utils.data.sampler import SubsetRandomSampler\nfrom torch.optim.lr_scheduler import StepLR, ReduceLROnPlateau, CosineAnnealingLR\n\nimport cv2\nimport albumentations\nfrom albumentations import torch as AT","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_data=pd.read_csv('../input/train.csv')\ntest_data=pd.read_csv('../input/test.csv')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"train_data['diagnosis'].value_counts().plot(kind='bar')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"fig=plt.figure(figsize=(25,16))\nfor id in sorted(train_data['diagnosis'].unique()):\n    for i,(idx,row) in enumerate(train_data.loc[train_data['diagnosis']==id].sample(6).iterrows()):\n        ax=fig.add_subplot(6,6,id*6+i+1,xticks=[],yticks=[])\n        im=Image.open(f\"../input/train_images/{row['id_code']}.png\")\n        plt.imshow(im)\n        ax.set_title(f'Label: {id}')","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"from sklearn.preprocessing import OneHotEncoder,LabelEncoder\n\ndef encode(y):\n    le=LabelEncoder()\n    integer_encoded=le.fit_transform(y)\n    one_hot_encoder=OneHotEncoder(sparse=False)\n    integer_encoded=integer_encoded.reshape(len(integer_encoded),1)\n    y=one_hot_encoder.fit_transform(integer_encoded)\n    return y,le\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"y,le=encode(train_data['diagnosis'])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"y.shape","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"class make_dataset(Dataset):\n    def __init__(self,df,transform,y=None,datatype='train'):\n        self.df=df\n        self.datatype=datatype\n        self.transform=transform\n        self.image_file_list=[f'../input/{datatype}_images/{i}.png' for i in df['id_code'].values]\n        if datatype=='train':\n            self.labels=y\n        else:\n            self.labels = np.zeros((df.shape[0], 5))\n        \n    def __len__(self):\n        return len(self.image_file_list)\n    \n    def __getitem__(self,idx):\n        img_name=self.image_file_list[idx]\n        img=Image.open(img_name)\n        img=self.transform(img)\n        label=self.labels[idx]\n        \n        if self.datatype=='train':\n            return img,label\n        else:\n            return img,label,img_name\n        \n        ","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"from skimage.transform import resize","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"tfms=transforms.Compose([transforms.Resize((224,224)),\n                              transforms.RandomHorizontalFlip(),\n                              transforms.ToTensor(),\n                              transforms.Normalize(mean=[0.485, 0.456, 0.406],std=[0.229, 0.224, 0.225])])","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"dataset=make_dataset(df=train_data,transform=tfms,y=y)\n\ntr, val = train_test_split(train_data.diagnosis, stratify=train_data.diagnosis, test_size=0.1)\ntrain_sampler = SubsetRandomSampler(list(tr.index))\nvalid_sampler = SubsetRandomSampler(list(val.index))\nbatch_size = 64\nnum_workers = 0\n\ntrain_loader = torch.utils.data.DataLoader(dataset, batch_size=batch_size, sampler=train_sampler, num_workers=num_workers)\nvalid_loader = torch.utils.data.DataLoader(dataset, batch_size=batch_size, sampler=valid_sampler, num_workers=num_workers)\n\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"test_dataset=make_dataset(df=test_data,transform=transforms.Compose([transforms.Resize((224,224)),\n                              transforms.ToTensor(),\n                              transforms.Normalize(mean=[0.485, 0.456, 0.406],std=[0.229, 0.224, 0.225])]),datatype='test')\n\ntest_loader = torch.utils.data.DataLoader(test_dataset, batch_size=batch_size, num_workers=num_workers)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"model_conv = torchvision.models.resnet50(pretrained=True)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"num_ftrs = model_conv.fc.in_features\nmodel_conv.fc = nn.Linear(2048, 5)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"model_conv.cuda()\ncriterion = nn.BCEWithLogitsLoss()\noptimizer = optim.Adam(model_conv.fc.parameters(), lr=0.01)\nscheduler = lr_scheduler.StepLR(optimizer, step_size=3, gamma=0.1)\nscheduler = lr_scheduler.ReduceLROnPlateau(optimizer, factor=0.8, patience=2, )","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"valid_loss_min = np.Inf\npatience = 5\n# current number of epochsimage = data_transforms(img)\n, where validation loss didn't increase\np = 0\n# whether training should be stopped\nstop = False\n\n# number of epochs to train the model\nimport os\nimport cv2\nimport matplotlib.pyplot as plt\n%matplotlib inline\n\nn_epochs = 20\nfor epoch in range(1, n_epochs+1):\n    print(time.ctime(), 'Epoch:', epoch)\n\n    train_loss = []\n    train_auc = []\n\n    for batch_i, (data, target) in enumerate(train_loader):\n\n        data, target = data.cuda(), target.cuda()\n\n        optimizer.zero_grad()\n        output = model_conv(data)\n        loss = criterion(output, target.float())\n        train_loss.append(loss.item())\n        \n        a = target.data.cpu().numpy()\n        b = output[:,-1].detach().cpu().numpy()\n        # train_auc.append(roc_auc_score(a, b))\n        loss.backward()\n        optimizer.step()\n    \n    model_conv.eval()\n    val_loss = []\n    val_auc = []\n    for batch_i, (data, target) in enumerate(valid_loader):\n        data, target = data.cuda(), target.cuda()\n        output = model_conv(data)\n\n        loss = criterion(output, target.float())\n\n        val_loss.append(loss.item()) \n        a = target.data.cpu().numpy()\n        b = output[:,-1].detach().cpu().numpy()\n        # val_auc.append(roc_auc_score(a, b))\n\n    # print(f'Epoch {epoch}, train loss: {np.mean(train_loss):.4f}, valid loss: {np.mean(val_loss):.4f}, train auc: {np.mean(train_auc):.4f}, valid auc: {np.mean(val_auc):.4f}')\n    print(f'Epoch {epoch}, train loss: {np.mean(train_loss):.4f}, valid loss: {np.mean(val_loss):.4f}.')\n    \n    valid_loss = np.mean(val_loss)\n    scheduler.step(valid_loss)\n    if valid_loss <= valid_loss_min:\n        print('Validation loss decreased ({:.6f} --> {:.6f}).  Saving model ...'.format(\n        valid_loss_min,\n        valid_loss))\n        torch.save(model_conv.state_dict(), 'model.pt')\n        valid_loss_min = valid_loss\n        p = 0\n\n    # check if validation loss didn't improve\n    if valid_loss > valid_loss_min:\n        p += 1\n        print(f'{p} epochs of increasing val loss')\n        if p > patience:\n            print('Stopping training')\n            stop = True\n            break        \n            \n    if stop:\n        break","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"sub = pd.read_csv('../input/sample_submission.csv')\n","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"sub = pd.read_csv('../input/sample_submission.csv')\n\nmodel_conv.eval()\nfor (data, target, name) in test_loader:\n    data = data.cuda()\n    output = model_conv(data)\n    output = output.cpu().detach().numpy()\n    for i, (e, n) in enumerate(list(zip(output, name))):\n        sub.loc[sub['id_code'] == n.split('/')[-1].split('.')[0], 'diagnosis'] = le.inverse_transform([np.argmax(e)])\n        \nsub.to_csv('submission.csv', index=False)","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"sub.head()","execution_count":null,"outputs":[]}],"metadata":{"kernelspec":{"display_name":"Python 3","language":"python","name":"python3"},"language_info":{"name":"python","version":"3.6.4","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"}},"nbformat":4,"nbformat_minor":1}