{"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":"# COVID-19 Detection with Cascade R-CNN 🦠🩺\n\n![Competition's Logo](https://storage.googleapis.com/kaggle-competitions/kaggle/26680/logos/header.png)","metadata":{"papermill":{"duration":0.022943,"end_time":"2021-05-20T09:49:20.26441","exception":false,"start_time":"2021-05-20T09:49:20.241467","status":"completed"},"pycharm":{"name":"#%% md\n"},"tags":[]}},{"cell_type":"markdown","source":"- *Author: Mariusz Wiśniewski*\n- *Competition: [SIIM-FISABIO-RSNA COVID-19 Detection](https://www.kaggle.com/competitions/siim-covid19-detection)*","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"markdown","source":"## Overview\n\nThis is a starter notebook that includes all of the tools required to preprocess the data, train the model, and generate a new submission.\n\n### Libraries Used\n\n- [PyTorch 🔥](https://pytorch.org)\n- [MMDetection ☄️](https://mmdetection.readthedocs.io/en/latest/)\n- [Weights&Biases 📈](https://wandb.ai/)\n\n### References\n\n- [Cascade R-CNN: High Quality Object Detection and Instance Segmentation 📃](https://arxiv.org/abs/1906.09756)\n- [Deep Residual Learning for Image Recognition 📃](https://arxiv.org/abs/1512.03385)\n- [SIIM MMDetection+CascadeRCNN+Weight&Bias 📓](https://www.kaggle.com/code/sreevishnudamodaran/siim-mmdetection-cascadercnn-weight-bias/notebook)","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"markdown","source":"## Project Setup","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"markdown","source":"### Installation of Additional Packages","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"!pip install mmcv-full -f https://download.openmmlab.com/mmcv/dist/cu110/torch1.7.0/index.html\n!git clone https://github.com/open-mmlab/mmdetection.git\n!cd mmdetection && pip install -e .","metadata":{"_kg_hide-output":true,"id":"RG3ZA4TYhFUx","outputId":"fd3c8d2b-da23-43aa-a8b1-4dab01cfdfcc","pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:30:47.326391Z","iopub.execute_input":"2022-05-30T02:30:47.326762Z","iopub.status.idle":"2022-05-30T02:31:55.919635Z","shell.execute_reply.started":"2022-05-30T02:30:47.326681Z","shell.execute_reply":"2022-05-30T02:31:55.918648Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Import Statements","metadata":{"papermill":{"duration":0.021449,"end_time":"2021-05-20T09:49:20.307797","exception":false,"start_time":"2021-05-20T09:49:20.286348","status":"completed"},"pycharm":{"name":"#%% md\n"},"tags":[]}},{"cell_type":"code","source":"import sys\n\nsys.path.insert(0, './mmdetection')\n\nimport os\n\nfrom mmdet.apis import set_random_seed\nfrom mmdet.datasets import build_dataset\nfrom mmdet.models import build_detector\nfrom mmdet.apis import train_detector\nfrom mmcv import Config\n\nimport numpy as np\nfrom pathlib import Path\nimport random\nimport torch","metadata":{"_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","_kg_hide-input":true,"_kg_hide-output":true,"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","papermill":{"duration":65.749573,"end_time":"2021-05-20T09:50:26.078998","exception":false,"start_time":"2021-05-20T09:49:20.329425","status":"completed"},"pycharm":{"name":"#%%\n"},"tags":[],"execution":{"iopub.status.busy":"2022-05-30T02:31:55.921579Z","iopub.execute_input":"2022-05-30T02:31:55.921974Z","iopub.status.idle":"2022-05-30T02:32:01.038614Z","shell.execute_reply.started":"2022-05-30T02:31:55.92193Z","shell.execute_reply":"2022-05-30T02:32:01.037608Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"import warnings\n\nwarnings.filterwarnings('ignore')","metadata":{"execution":{"iopub.status.busy":"2022-05-30T02:32:01.041298Z","iopub.execute_input":"2022-05-30T02:32:01.041871Z","iopub.status.idle":"2022-05-30T02:32:01.046989Z","shell.execute_reply.started":"2022-05-30T02:32:01.0418Z","shell.execute_reply":"2022-05-30T02:32:01.045428Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Weights & Biases Setup","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"import wandb\nfrom kaggle_secrets import UserSecretsClient\n\nuser_secrets = UserSecretsClient()\nwandb_api = user_secrets.get_secret('WANDB_API_KEY')\n\nwandb.login(key=wandb_api)","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:32:01.049168Z","iopub.execute_input":"2022-05-30T02:32:01.049541Z","iopub.status.idle":"2022-05-30T02:32:04.082785Z","shell.execute_reply.started":"2022-05-30T02:32:01.049506Z","shell.execute_reply":"2022-05-30T02:32:04.081801Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Imports and Seed Everything","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"global_seed = 2022\n\n\ndef set_seed(seed=global_seed):\n    \"\"\"Sets the random seeds.\"\"\"\n    set_random_seed(seed, deterministic=False)\n    random.seed(seed)\n    np.random.seed(seed)\n    torch.manual_seed(seed)\n    torch.cuda.manual_seed(seed)\n    torch.backends.cudnn.deterministic = True\n    torch.backends.cudnn.benchmark = False\n    os.environ['PYTHONHASHSEED'] = str(seed)\n\n\nset_seed()","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:32:04.084321Z","iopub.execute_input":"2022-05-30T02:32:04.084744Z","iopub.status.idle":"2022-05-30T02:32:04.096004Z","shell.execute_reply.started":"2022-05-30T02:32:04.0847Z","shell.execute_reply":"2022-05-30T02:32:04.095201Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"## Prepare the MMDetection Config","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"markdown","source":"### General Training Settings","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"model_name = 'cascade_rcnn_x101_32x4d_fpn_1x'\nfold = 0\njob = 1\n\nbaseline_cfg_path = f'/kaggle/working/mmdetection/configs/cascade_rcnn/{model_name}_coco.py'\ncfg = Config.fromfile(baseline_cfg_path)\n\n# Folder to store model logs and weight files\njob_folder = f'/kaggle/working/job{job}_{model_name}_fold{fold}'\ncfg.work_dir = job_folder\n\n# Set seed thus the results are more reproducible\ncfg.seed = global_seed\n\nif not os.path.exists(job_folder):\n    os.makedirs(job_folder)\n\nprint('Job folder:', job_folder)","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:32:04.097495Z","iopub.execute_input":"2022-05-30T02:32:04.097992Z","iopub.status.idle":"2022-05-30T02:32:04.128076Z","shell.execute_reply.started":"2022-05-30T02:32:04.097903Z","shell.execute_reply":"2022-05-30T02:32:04.127305Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Set the number of classes\nfor head in cfg.model.roi_head.bbox_head:\n    head.num_classes = 1\n\ncfg.runner.max_epochs = 20  # Epochs for the runner that runs the workflow\ncfg.total_epochs = 20\n\n# Learning rate of optimizers. The LR is divided by 8 since the config file is originally for 8 GPUs\ncfg.optimizer.lr = 0.02 / 8\n\n## Learning rate scheduler config used to register LrUpdater hook\ncfg.lr_config = dict(\n    policy='CosineAnnealing',\n    # The policy of scheduler, also support CosineAnnealing, Cyclic, etc. Refer to details of supported LrUpdater from https://github.com/open-mmlab/mmcv/blob/master/mmcv/runner/hooks/lr_updater.py#L9.\n    by_epoch=False,\n    warmup='linear',  # The warmup policy, also support `exp` and `constant`.\n    warmup_iters=500,  # The number of iterations for warmup\n    warmup_ratio=0.001,  # The ratio of the starting learning rate used for warmup\n    min_lr=1e-6)\n\n# config to register logger hook\ncfg.log_config.interval = 20  # Interval to print the log\n\n# Config to set the checkpoint hook, Refer to https://github.com/open-mmlab/mmcv/blob/master/mmcv/runner/hooks/checkpoint.py for implementation.\ncfg.checkpoint_config.interval = 1  # The save interval is 1\n\ncfg.gpu_ids = [0]\ncfg.device = 'cuda'","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:38:49.053931Z","iopub.execute_input":"2022-05-30T02:38:49.054291Z","iopub.status.idle":"2022-05-30T02:38:49.060858Z","shell.execute_reply.started":"2022-05-30T02:38:49.054257Z","shell.execute_reply":"2022-05-30T02:38:49.059806Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Configure Datasets for Training and Evaluation","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"cfg.dataset_type = 'CocoDataset'  # Dataset type, this will be used to define the dataset\ncfg.classes = ('Covid_Abnormality',)\n\ncfg.data.train.img_prefix = '/kaggle/input/siim-covid19-512-images-and-metadata/train'  # Prefix of image path\ncfg.data.train.classes = cfg.classes\ncfg.data.train.ann_file = f'/kaggle/input/siim-covid19-coco-512x512-groupkfold/train_annotations_fold{fold}.json'\ncfg.data.train.type = 'CocoDataset'\n\ncfg.data.val.img_prefix = '/kaggle/input/siim-covid19-512-images-and-metadata/train'  # Prefix of image path\ncfg.data.val.classes = cfg.classes\ncfg.data.val.ann_file = f'/kaggle/input/siim-covid19-coco-512x512-groupkfold/val_annotations_fold{fold}.json'\ncfg.data.val.type = 'CocoDataset'\n\ncfg.data.test.img_prefix = '/kaggle/input/siim-covid19-512-images-and-metadata/train'  # Prefix of image path\ncfg.data.test.classes = cfg.classes\ncfg.data.test.ann_file = f'/kaggle/input/siim-covid19-coco-512x512-groupkfold/val_annotations_fold{fold}.json'\ncfg.data.test.type = 'CocoDataset'\n\ncfg.data.samples_per_gpu = 4  # Batch size of a single GPU used in testing\ncfg.data.workers_per_gpu = 2  # Worker to pre-fetch data for each single GPU","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:35:04.138693Z","iopub.execute_input":"2022-05-30T02:35:04.139052Z","iopub.status.idle":"2022-05-30T02:35:04.146181Z","shell.execute_reply.started":"2022-05-30T02:35:04.139015Z","shell.execute_reply":"2022-05-30T02:35:04.145004Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Setting Metric for Evaluation","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"# The config to build the evaluation hook, refer to https://github.com/open-mmlab/mmdetection/blob/master/mmdet/core/evaluation/eval_hooks.py#L7 for more details.\ncfg.evaluation.metric = 'bbox'  # Metrics used during evaluation\n\n# Set the epoch intervel to perform evaluation\ncfg.evaluation.interval = 1\n\ncfg.evaluation.save_best='bbox_mAP_50'","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:35:29.148318Z","iopub.execute_input":"2022-05-30T02:35:29.148648Z","iopub.status.idle":"2022-05-30T02:35:29.153178Z","shell.execute_reply.started":"2022-05-30T02:35:29.148614Z","shell.execute_reply":"2022-05-30T02:35:29.152181Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Prepare the Pre-processing & Augmentation Pipelines","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"albu_train_transforms = [\n    dict(type='ShiftScaleRotate', shift_limit=0.0625,\n         scale_limit=0.15, rotate_limit=15, p=0.4),\n    dict(type='RandomBrightnessContrast', brightness_limit=0.2,\n         contrast_limit=0.2, p=0.5),\n    dict(type='IAAAffine', shear=(-10.0, 10.0), p=0.4),\n    #     dict(type='MixUp', p=0.2, lambd=0.5),\n    dict(type='Blur', p=1.0, blur_limit=7),\n    dict(type='CLAHE', p=0.5),\n    dict(type='Equalize', mode='cv', p=0.4),\n    dict(\n        type='OneOf',\n        transforms=[\n            dict(type='GaussianBlur', p=1.0, blur_limit=7),\n            dict(type='MedianBlur', p=1.0, blur_limit=7),\n        ],\n        p=0.4,\n    )\n]\n\ncfg.train_pipeline = [\n    dict(type='LoadImageFromFile'),\n    dict(type='LoadAnnotations', with_bbox=True, with_mask=True),\n    dict(type='Resize', img_scale=(1333, 800), keep_ratio=True),\n    dict(type='RandomFlip', flip_ratio=0.5),\n    dict(\n        type='Albu',\n        transforms=albu_train_transforms,\n        bbox_params=dict(\n            type='BboxParams',\n            format='pascal_voc',\n            label_fields=['gt_labels'],\n            min_visibility=0.0,\n            filter_lost_elements=True),\n        keymap=dict(img='image', gt_bboxes='bboxes'),\n        update_pad_shape=False,\n        skip_img_without_anno=True),\n    dict(\n        type='Normalize',\n        mean=[123.675, 116.28, 103.53],\n        std=[58.395, 57.12, 57.375],\n        to_rgb=True),\n    dict(type='Pad', size_divisor=32),\n    dict(type='DefaultFormatBundle'),\n    dict(type='Collect', keys=['img', 'gt_bboxes', 'gt_labels', 'gt_masks'])\n]\ncfg.test_pipeline = [\n    dict(type='LoadImageFromFile'),\n    dict(\n        type='MultiScaleFlipAug',\n        img_scale=(1333, 800),\n        flip=False,\n        transforms=[\n            dict(type='Resize', keep_ratio=True),\n            dict(type='RandomFlip'),\n            dict(\n                type='Normalize',\n                mean=[123.675, 116.28, 103.53],\n                std=[58.395, 57.12, 57.375],\n                to_rgb=True),\n            dict(type='Pad', size_divisor=32),\n            dict(type='ImageToTensor', keys=['img']),\n            dict(type='Collect', keys=['img'])\n        ])\n]","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:35:33.007658Z","iopub.execute_input":"2022-05-30T02:35:33.008022Z","iopub.status.idle":"2022-05-30T02:35:33.021801Z","shell.execute_reply.started":"2022-05-30T02:35:33.007984Z","shell.execute_reply":"2022-05-30T02:35:33.020529Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Weights & Biases Integration for Experiment Tracking and Logging","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"cfg.log_config.hooks = [dict(type='TextLoggerHook'),\n                        dict(type='WandbLoggerHook',\n                             init_kwargs=dict(project=user_secrets.get_secret(\n                                                  'WANDB_PROJECT'),\n                                              entity=user_secrets.get_secret(\n                                                  'WANDB_ENTITY'),\n                                              name=f'8-mw-{model_name}-fold{fold}-job{job}',\n                                              ))\n                        ]","metadata":{"pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:39:59.445453Z","iopub.execute_input":"2022-05-30T02:39:59.44578Z","iopub.status.idle":"2022-05-30T02:40:00.41889Z","shell.execute_reply.started":"2022-05-30T02:39:59.445747Z","shell.execute_reply":"2022-05-30T02:40:00.418035Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Save Config File","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"cfg_path = f'{job_folder}/job{job}_{Path(baseline_cfg_path).name}'\nprint(cfg_path)\n\n# Save config file for later inference\ncfg.dump(cfg_path)\nprint(f'Config:\\n{cfg.pretty_text}')","metadata":{"_kg_hide-output":true,"id":"9C8s78L_hY2P","outputId":"5c532360-7684-42e1-bb2b-e59377576c2e","pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:36:09.770758Z","iopub.execute_input":"2022-05-30T02:36:09.771165Z","iopub.status.idle":"2022-05-30T02:36:13.209311Z","shell.execute_reply.started":"2022-05-30T02:36:09.771127Z","shell.execute_reply":"2022-05-30T02:36:13.206892Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### 🚀 Build Dataset and Start Training","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"model = build_detector(cfg.model,\n                       train_cfg=cfg.get('train_cfg'),\n                       test_cfg=cfg.get('test_cfg'))\nmodel.init_weights()","metadata":{"id":"o6u_0gZuhcUy","outputId":"557284a4-a687-474a-aa4d-2abbb8fb403c","pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:36:35.639884Z","iopub.execute_input":"2022-05-30T02:36:35.640523Z","iopub.status.idle":"2022-05-30T02:37:02.004631Z","shell.execute_reply.started":"2022-05-30T02:36:35.640482Z","shell.execute_reply":"2022-05-30T02:37:02.003864Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"datasets = [build_dataset(cfg.data.train)]","metadata":{"id":"om_JbWv9heIQ","outputId":"0f264828-5b49-4a30-b035-9635424cd2d1","pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:37:24.311647Z","iopub.execute_input":"2022-05-30T02:37:24.312017Z","iopub.status.idle":"2022-05-30T02:37:24.4188Z","shell.execute_reply.started":"2022-05-30T02:37:24.311982Z","shell.execute_reply":"2022-05-30T02:37:24.417756Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"train_detector(model, datasets[0], cfg, distributed=False, validate=True)","metadata":{"id":"anIjmmhVhgKE","outputId":"9a97104b-5d08-4aa7-ce9c-be376e789ea5","pycharm":{"name":"#%%\n"},"execution":{"iopub.status.busy":"2022-05-30T02:40:09.245346Z","iopub.execute_input":"2022-05-30T02:40:09.245674Z","iopub.status.idle":"2022-05-30T02:58:15.030685Z","shell.execute_reply.started":"2022-05-30T02:40:09.245642Z","shell.execute_reply":"2022-05-30T02:58:15.028789Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# Get the best epoch number\nimport json\n\nfrom collections import defaultdict\n\nlog_file = f'{job_folder}/None.log.json'\n\n\n# Source: mmdetection/tools/analysis_tools/analyze_logs.py\ndef load_json_logs(json_logs):\n    # load and convert json_logs to log_dict, key is epoch, value is a sub dict\n    # keys of sub dict is different metrics, e.g. memory, bbox_mAP\n    # value of sub dict is a list of corresponding values of all iterations\n    log_dicts = [dict() for _ in json_logs]\n    for json_log, log_dict in zip(json_logs, log_dicts):\n        with open(json_log, 'r') as log_file:\n            for line in log_file:\n                log = json.loads(line.strip())\n                # skip lines without `epoch` field\n                if 'epoch' not in log:\n                    continue\n                epoch = log.pop('epoch')\n                if epoch not in log_dict:\n                    log_dict[epoch] = defaultdict(list)\n                for k, v in log.items():\n                    log_dict[epoch][k].append(v)\n    return log_dicts\n\n\nlog_dict = load_json_logs([log_file])\n# [(print(inner['bbox_mAP']) for inner in item) for item in log_dict]\n# [print(item) for item in log_dict[0]]\nbest_epoch = np.argmax([item['bbox_mAP'][0] for item in log_dict[0].values()]) + 1\nbest_epoch","metadata":{"execution":{"iopub.execute_input":"2021-07-16T20:13:19.835119Z","iopub.status.busy":"2021-07-16T20:13:19.834786Z","iopub.status.idle":"2021-07-16T20:13:19.856441Z","shell.execute_reply":"2021-07-16T20:13:19.855516Z","shell.execute_reply.started":"2021-07-16T20:13:19.835086Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"model_files = [f'{job_folder}/epoch_{best_epoch}.pth',\n               cfg_path\n               ]\n\n# Create a new wnb run for saving models as artifacts\nrun = wandb.init(project=user_secrets.get_secret('WANDB_PROJECT'),\n                 name=f'models_files_{model_name}_fold{fold}_job{job}',\n                 entity=user_secrets.get_secret('WANDB_ENTITY'),\n                 group='Artifact',\n                 job_type='model-files')\n\nartifact = wandb.Artifact(f'models_files_{model_name}_fold{fold}_job{job}', type='model')\n\nfor model_file in model_files:\n    artifact.add_file(model_file)\n\nrun.log_artifact(artifact)\nrun.finish()","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:32.342823Z","iopub.status.busy":"2021-06-01T13:08:32.340664Z","iopub.status.idle":"2021-06-01T13:08:53.218949Z","shell.execute_reply":"2021-06-01T13:08:53.217832Z","shell.execute_reply.started":"2021-06-01T13:08:32.342746Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"## Inference and Visualize Output","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"from mmdet.apis import init_detector, inference_detector\n\nimport matplotlib.pyplot as plt\nimport pandas as pd\nimport cv2","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:53.220908Z","iopub.status.busy":"2021-06-01T13:08:53.220548Z","iopub.status.idle":"2021-06-01T13:08:53.226675Z","shell.execute_reply":"2021-06-01T13:08:53.225717Z","shell.execute_reply.started":"2021-06-01T13:08:53.220868Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"with open('../input/siim-covid19-coco-512x512-groupkfold/val_annotations_fold0.json') as f:\n    val_ann = json.load(f)\nimage_paths = [item['file_name'] for item in val_ann['images'][:9]]\n\ndf_annotations = pd.read_csv('../input/siim-covid19-512-images-and-metadata/df_train_processed_meta.csv')","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:53.228554Z","iopub.status.busy":"2021-06-01T13:08:53.228173Z","iopub.status.idle":"2021-06-01T13:08:53.284857Z","shell.execute_reply":"2021-06-01T13:08:53.284042Z","shell.execute_reply.started":"2021-06-01T13:08:53.228517Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"def draw_bbox(image,\n              box,\n              label,\n              color,\n              label_size=0.5,\n              alpha_box=0.3,\n              alpha_label=0.6):\n    overlay_bbox = image.copy()\n    overlay_label = image.copy()\n    output = image.copy()\n\n    text_width, text_height = cv2.getTextSize(label.upper(),\n                                              cv2.FONT_HERSHEY_SIMPLEX, label_size, 1)[0]\n    cv2.rectangle(overlay_bbox, (box[0], box[1]), (box[2], box[3]),\n                  color, -1)\n    cv2.addWeighted(overlay_bbox, alpha_box, output, 1 - alpha_box, 0, output)\n\n    cv2.rectangle(overlay_label, (box[0], box[1] - 7 - text_height),\n                  (box[0] + text_width + 2, box[1]), (0, 0, 0), -1)\n    cv2.addWeighted(overlay_label, alpha_label, output, 1 - alpha_label, 0, output)\n    output = cv2.rectangle(output, (box[0], box[1]), (box[2], box[3]),\n                           color, 2)\n    cv2.putText(output, label.upper(), (box[0], box[1] - 5),\n                cv2.FONT_HERSHEY_SIMPLEX, label_size, (255, 255, 255), 1, cv2.LINE_AA)\n    return output","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:53.28841Z","iopub.status.busy":"2021-06-01T13:08:53.288056Z","iopub.status.idle":"2021-06-01T13:08:53.299619Z","shell.execute_reply":"2021-06-01T13:08:53.298665Z","shell.execute_reply.started":"2021-06-01T13:08:53.288357Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"checkpoint = f'{job_folder}/epoch_{best_epoch}.pth'\n\nprint('Loading weights from:', checkpoint)\ncfg = Config.fromfile(cfg_path)\nmodel = init_detector(cfg, checkpoint, device='cuda:0')","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:53.301573Z","iopub.status.busy":"2021-06-01T13:08:53.301264Z","iopub.status.idle":"2021-06-01T13:08:54.519893Z","shell.execute_reply":"2021-06-01T13:08:54.51902Z","shell.execute_reply.started":"2021-06-01T13:08:53.301546Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"new_size = (512, 512)\nimgs_path = '/kaggle/input/siim-covid19-512-images-and-metadata/train'\nthreshold = 0.45\n\nfig, axes = plt.subplots(3, 3, figsize=(19, 21))\nfig.subplots_adjust(hspace=0.2, wspace=0.2)\naxes = axes.ravel()\n\nresults_list = []\n\nfor idx, img_id in enumerate(image_paths):\n    img_path = os.path.join(imgs_path, img_id)\n    img = cv2.imread(img_path)\n    result = inference_detector(model, img_path)\n    results_filtered = result[0][result[0][:, 4] > threshold]\n    bboxes = results_filtered[:, :4]\n    scores = results_filtered[:, 4]\n    results_list.append(result[0])\n\n    for box in bboxes:\n        img = draw_bbox(img, list(np.int_(box)), 'Covid_Abnormality',\n                        (255, 243, 0))\n\n    axes[idx].imshow(img, cmap='gray')\n    axes[idx].set_title(img_id, size=18, pad=30)\n    axes[idx].set_xticklabels([])\n    axes[idx].set_yticklabels([])","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:54.526014Z","iopub.status.busy":"2021-06-01T13:08:54.524063Z","iopub.status.idle":"2021-06-01T13:08:57.110328Z","shell.execute_reply":"2021-06-01T13:08:57.109364Z","shell.execute_reply.started":"2021-06-01T13:08:54.525971Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"### Interactively Visualize & Analyze Output in Dashboard","metadata":{"pycharm":{"name":"#%% md\n"}}},{"cell_type":"code","source":"run = wandb.init(project=user_secrets.get_secret('WANDB_PROJECT'),\n                 name=f'images-{model_name}-fold{fold}-job{job}',\n                 job_type='images')\n\nclass_id_to_label = {\n    1: 'pred_covid_abnormality',\n    2: 'GT_covid_abnormality'\n}\n\nwnb_images = []\n\nfor img_id, result in zip(image_paths, results_list):\n\n    bboxes = result[:, :4]\n    scores = result[:, 4]\n    ann_dict = {'predictions': {\n        'box_data': [],\n        'class_labels': class_id_to_label\n    },\n        'ground_truth': {\n            'box_data': [],\n            'class_labels': class_id_to_label\n        }\n    }\n\n    for box, score in zip(bboxes, scores):\n        single_data = {\n            # one box expressed in the default relative/fractional domain\n            'position': {\n                'minX': round(float(box[0]) / 512, 3),\n                'maxX': round(float(box[2]) / 512, 3),\n                'minY': round(float(box[1]) / 512, 3),\n                'maxY': round(float(box[3]) / 512, 3),\n            },\n            'class_id': 1,\n            'box_caption': class_id_to_label[1],\n            'scores': {\n                'confidence': float(score),\n            }\n        }\n        ann_dict['predictions']['box_data'].append(single_data)\n\n    image_annotations = df_annotations[df_annotations.id == img_id.strip('.png')]\n\n    for idxx, row in image_annotations[['xmin', 'ymin', 'xmax', 'ymax']].iterrows():\n        single_data = {\n            # one box expressed in the default relative/fractional domain\n            'position': {\n                'minX': round(float(row[0]) / 512, 3),\n                'maxX': round(float(row[2]) / 512, 3),\n                'minY': round(float(row[1]) / 512, 3),\n                'maxY': round(float(row[3]) / 512, 3),\n            },\n            'class_id': 2,\n            'box_caption': class_id_to_label[2],\n            'scores': {\n                'confidence': 1.0,\n            }\n        }\n        ann_dict['ground_truth']['box_data'].append(single_data)\n\n    image = cv2.imread(os.path.join(imgs_path, img_id))\n    wnb_images.append(wandb.Image(image, boxes=ann_dict))\n\nwandb.log({f'images-{model_name}-fold{fold}-job{job}': wnb_images})\n\nrun.finish()\nrun","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:08:57.111952Z","iopub.status.busy":"2021-06-01T13:08:57.111645Z","iopub.status.idle":"2021-06-01T13:09:07.633874Z","shell.execute_reply":"2021-06-01T13:09:07.632878Z","shell.execute_reply.started":"2021-06-01T13:08:57.111919Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"!rm -rf mmdetection/","metadata":{"execution":{"iopub.execute_input":"2021-06-01T13:09:07.635865Z","iopub.status.busy":"2021-06-01T13:09:07.635452Z","iopub.status.idle":"2021-06-01T13:09:07.842737Z","shell.execute_reply":"2021-06-01T13:09:07.841587Z","shell.execute_reply.started":"2021-06-01T13:09:07.63582Z"},"pycharm":{"name":"#%%\n"},"trusted":true},"execution_count":null,"outputs":[]}]}