{"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":"code","source":"","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Prepare to install MASK2FORMER**\n\nhttps://github.com/facebookresearch/Mask2Former","metadata":{}},{"cell_type":"markdown","source":"***Warning : After below installing, Must RESTART KERNEL***","metadata":{}},{"cell_type":"code","source":"\n## preparing environment\n!pip uninstall pytorch -y\n!pip install torch==1.9.0+cu111 torchvision==0.10.0+cu111 torchaudio==0.9.0 -f https://download.pytorch.org/whl/torch_stable.html\n!pip install pyyaml==5.1\n\nimport torch\nTORCH_VERSION = \".\".join(torch.__version__.split(\".\")[:2])\nCUDA_VERSION = torch.__version__.split(\"+\")[-1]\nprint(\"torch: \", TORCH_VERSION, \"; cuda: \", CUDA_VERSION)\n!python -m pip install detectron2 -f https://dl.fbaipublicfiles.com/detectron2/wheels/cu111/torch1.9/index.html\n!pip install -U opencv-python\n!pip install Ninja\n\n# Git Mask2Former\n!git clone https://github.com/facebookresearch/Mask2Former.git\n%cd Mask2Former\n!pip install git+https://github.com/cocodataset/panopticapi.git\n!pip install -r requirements.txt\n%cd mask2former/modeling/pixel_decoder/ops\n!python setup.py build install\n%cd ../../../../\n\n%cd Mask2Former/mask2former/modeling/pixel_decoder/ops\n!sh make.sh\n\n%cd ../../../../../Mask2Former/\n\n","metadata":{"execution":{"iopub.status.busy":"2022-12-22T06:24:59.08078Z","iopub.execute_input":"2022-12-22T06:24:59.081658Z","iopub.status.idle":"2022-12-22T06:25:02.564197Z","shell.execute_reply.started":"2022-12-22T06:24:59.081558Z","shell.execute_reply":"2022-12-22T06:25:02.559923Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**IMPORT LIBRARIES**","metadata":{}},{"cell_type":"code","source":"","metadata":{"execution":{"iopub.status.busy":"2022-09-22T13:52:25.02961Z","iopub.execute_input":"2022-09-22T13:52:25.030815Z","iopub.status.idle":"2022-09-22T13:52:26.029448Z","shell.execute_reply.started":"2022-09-22T13:52:25.030776Z","shell.execute_reply":"2022-09-22T13:52:26.028207Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"# import some common detectron2 utilities\nimport detectron2\nfrom detectron2.utils.logger import setup_logger\nfrom detectron2 import model_zoo\nfrom detectron2.engine import DefaultPredictor, DefaultTrainer\nfrom detectron2.config import get_cfg\nfrom detectron2.utils.visualizer import Visualizer, ColorMode\nfrom detectron2.data import MetadataCatalog\nfrom detectron2.projects.deeplab import add_deeplab_config, build_lr_scheduler\nfrom detectron2.data.datasets import register_coco_instances, load_coco_json\nimport detectron2.utils.comm as comm\nfrom detectron2.solver.build import maybe_add_gradient_clipping\nfrom mask2former import (\n    add_maskformer2_config, \n    MaskFormerInstanceDatasetMapper,\n)\nfrom sklearn.model_selection import StratifiedKFold\nfrom matplotlib import units\nfrom detectron2.data import DatasetCatalog, MetadataCatalog, build_detection_train_loader\nimport os\nimport pandas as pd\nimport tifffile as tiff\nimport matplotlib.pyplot as plt\nimport json\nimport cv2\nimport glob\nimport matplotlib.patches as mpatches\nimport numpy as np\nimport cv2\nfrom tqdm.auto import tqdm\nimport random\nimport torch\nimport copy\n\nsetup_logger()\nsetup_logger(name=\"mask2former\")\n\t\n ","metadata":{"execution":{"iopub.status.busy":"2022-09-22T15:05:05.772435Z","iopub.execute_input":"2022-09-22T15:05:05.772821Z","iopub.status.idle":"2022-09-22T15:05:05.785753Z","shell.execute_reply.started":"2022-09-22T15:05:05.772789Z","shell.execute_reply":"2022-09-22T15:05:05.784696Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**View**","metadata":{}},{"cell_type":"code","source":"DF = \"../../input/hubmap-organ-segmentation\"\ntrain_path = os.path.join(DF, \"train.csv\")\ntest_path = os.path.join(DF, \"test.csv\")\nsub_path = os.path.join(DF, \"sample_submission.csv\")\ndf_train = pd.read_csv(train_path)\ndf_test = pd.read_csv(test_path)\ndf_sub = pd.read_csv(sub_path)\n\ndata_num = 10392\n\ntrain_csv = pd.read_csv(f\"{DF}/train.csv\")\nprint(train_csv.dtypes)\nprint(train_csv[\"id\"][0])\n\nresults = list(map(int, train_csv[\"rle\"][0].split(' ')))\n#shape of image \ntrain_img = tiff.imread(f\"{DF}/train_images/{data_num}.tiff\")\ntest_img = tiff.imread(f\"{DF}/test_images/10078.tiff\")\nprint(train_img.shape)\nprint(test_img.shape)\n\nplt.figure(0)\nplt.subplot(1,2,1)\ntrain_c = plt.imshow(train_img)\n\n# make raw image (white)\nraw_img = np.ones(train_img.shape, dtype=np.int32)\n\n_file = open(f\"{DF}/train_annotations/{data_num}.json\")\ndata_file = json.load(_file)\nfor cell_num, cell_polygon in enumerate(data_file) :\n    \n    pts = np.array(cell_polygon, dtype=np.int32)[np.newaxis,:,:]\n    \n    cv2.fillConvexPoly(raw_img, pts, (0,255,0))\nplt.subplot(1,2,2)\nplt.imshow(raw_img)\nplt.figure(1)\n\ntest_c = plt.imshow(test_img)\n\n\nplt.show()\n","metadata":{"execution":{"iopub.status.busy":"2022-09-22T13:53:35.454812Z","iopub.execute_input":"2022-09-22T13:53:35.455385Z","iopub.status.idle":"2022-09-22T13:53:39.086611Z","shell.execute_reply.started":"2022-09-22T13:53:35.455329Z","shell.execute_reply":"2022-09-22T13:53:39.085698Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"cfgDict = {\n    \"dicomPath\": None,\n    \"orgDataPath\": None,\n    \"trainJsonPath\": None,\n    \"validJsonPath\": None,\n    \"newDataPath\": \"../input/hubmap-organ-segmentation/train_images/\",\n    \"cachePath\": \"./\",\n    \"splitCfgFilePath\": \"./splitCfg.json\",\n    \"annotationPath\": \"../input/hubmap-hpa-coco-dataset/annotations.json\",\n    \"newAnnotationPath\": \"./train.json\",\n    \"trainDataName\": \"hubmapTrain\",\n    \"validDataName\": \"hubmapValid\",\n    \"sampleSize\": 50,\n    \"imSize\": None,\n    \"modelName\": \"COCO-InstanceSegmentation/mask_rcnn_R_50_FPN_3x.yaml\",\n    \"mask_format\": \"bitmask\",\n    \"debug\": True,\n    \"outdir\": \"./results/\",\n    \"logFile\": \"log.txt\",\n    \"splitMode\": True,\n    \"seed\": 111,\n    \"device\": \"cuda\",\n    \"iter\": 100,\n    \"ims_per_batch\": 4,\n    \"roi_batch_size_per_image\": 128,\n    \"eval_period\": 10,\n    \"lr_scheduler_name\": \"WarmupCosineLR\",\n    \"base_lr\": 0.001,\n    \"checkpoint_period\":100,\n    \"num_workers\": 2,\n    \"score_thresh_test\": 0.5,\n    \"augKwargs\": {\n        \"RandomFlip\": {\"prob\": 0.5},\n        \"RandomRotation\": {\"angle\": [0,360]},\n        \"Resize\":{\"shape\":(128,128)}\n    },\n    \"thing_classes\": [\"prostate\",\"spleen\",\"lung\",\"kidney\",\"largeintestine\"]\n}\n","metadata":{"execution":{"iopub.status.busy":"2022-09-22T13:55:48.169237Z","iopub.execute_input":"2022-09-22T13:55:48.169621Z","iopub.status.idle":"2022-09-22T13:55:48.177316Z","shell.execute_reply.started":"2022-09-22T13:55:48.169588Z","shell.execute_reply":"2022-09-22T13:55:48.175994Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**DIRECTORY**","metadata":{}},{"cell_type":"code","source":"\ndata_num = 10392\nimg = tiff.imread(f\"{DF}/train_images/{data_num}.tiff\")\nprint(img.shape)\nfig = plt.figure()\n\n#plt.imshow(img)\nax1 = fig.add_subplot(1, 2, 1)\nax1.imshow(img)\nax1.set_title('RAW')\nax1.axis(\"off\")\n\n_file = open(f\"{DF}/train_annotations/{data_num}.json\")\ndata_file = json.load(_file)\nfor cell_num, cell_polygon in enumerate(data_file) :\n    \n    pts = np.array(cell_polygon, dtype=np.int32)[np.newaxis,:,:]\n    \n    cv2.fillConvexPoly(img,pts,0)\n\n#plt.imshow(img)\n\nax2 = fig.add_subplot(1, 2, 2)\nax2.imshow(img)\nax2.set_title('Withered trees')\nax2.axis(\"off\")\n \nplt.show()\n\n","metadata":{"execution":{"iopub.status.busy":"2022-09-22T13:56:43.894892Z","iopub.execute_input":"2022-09-22T13:56:43.895953Z","iopub.status.idle":"2022-09-22T13:56:45.649621Z","shell.execute_reply.started":"2022-09-22T13:56:43.895913Z","shell.execute_reply":"2022-09-22T13:56:45.648617Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Rle Encode**","metadata":{}},{"cell_type":"code","source":"def mask2rle(mask):\n    ''' takes a 2d boolean numpy array and turns it into a space-delimited RLE string '''\n    \n    mask = mask.T.reshape(-1) # make 1D, column-first\n    mask = np.pad(mask, 1) # make sure that the 1d mask starts and ends with a 0\n    starts = np.nonzero((~mask[:-1]) & mask[1:])[0] # start points\n    ends = np.nonzero(mask[:-1] & (~mask[1:]))[0] # end points\n    rle = np.empty(2 * starts.size, dtype=int) # interlacing...\n    rle[0::2] = starts # ...starts...\n    rle[1::2] = ends - starts # ...and lengths\n    rle = ' '.join([ str(elem) for elem in rle ]) # turn into space-separated string\n    return rle","metadata":{"execution":{"iopub.status.busy":"2022-09-22T14:31:42.142055Z","iopub.execute_input":"2022-09-22T14:31:42.142655Z","iopub.status.idle":"2022-09-22T14:31:42.151464Z","shell.execute_reply.started":"2022-09-22T14:31:42.142618Z","shell.execute_reply":"2022-09-22T14:31:42.150498Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"class COCOTrainer(DefaultTrainer):\n\n    @classmethod\n    def build_evaluator(cls, cfg, dataset_name, output_folder=None):\n        \"\"\"\n        Create evaluator(s) for a given dataset.\n        This uses the special metadata \"evaluator_type\" associated with each\n        builtin dataset. For your own dataset, you can simply create an\n        evaluator manually in your script and do not have to worry about the\n        hacky if-else logic here.\n        \"\"\"\n    @classmethod\n    def build_evaluator(cls, cfg, datasetName, outputFolder=None):\n        if output_folder is None:\n            output_folder = os.path.join(cfg.OUTPUT_DIR, \"inference\")\n        return COCOEvaluator(datasetName, (\"bbox\",), False, output_dir=outputFolder)\n\n\n    @classmethod\n    def build_train_loader(cls, cfg):\n        # Semantic segmentation dataset mapper\n        if cfg.INPUT.DATASET_MAPPER_NAME == \"mask_former_instance\":\n            mapper = MaskFormerInstanceDatasetMapper(cfg, True)\n        return build_detection_train_loader(cfg, mapper=mapper)\n    \n    @classmethod\n    def build_test_loader(cls, cfg, datasetName):\n        return build_detection_test_loader(\n            cfg, datasetName, mapper=AugMapper(cfg, False)\n        )\n    \n    @classmethod\n    def build_lr_scheduler(cls, cfg, optimizer):\n        \"\"\"\n        It now calls :func:`detectron2.solver.build_lr_scheduler`.\n        Overwrite it if you'd like a different scheduler.\n        \"\"\"\n        return build_lr_scheduler(cfg, optimizer)\n\n    @classmethod\n    def build_optimizer(cls, cfg, model):\n        weight_decay_norm = cfg.SOLVER.WEIGHT_DECAY_NORM\n        weight_decay_embed = cfg.SOLVER.WEIGHT_DECAY_EMBED\n\n        defaults = {}\n        defaults[\"lr\"] = cfg.SOLVER.BASE_LR\n        defaults[\"weight_decay\"] = cfg.SOLVER.WEIGHT_DECAY\n\n        norm_module_types = (\n            torch.nn.BatchNorm1d,\n            torch.nn.BatchNorm2d,\n            torch.nn.BatchNorm3d,\n            torch.nn.SyncBatchNorm,\n            # NaiveSyncBatchNorm inherits from BatchNorm2d\n            torch.nn.GroupNorm,\n            torch.nn.InstanceNorm1d,\n            torch.nn.InstanceNorm2d,\n            torch.nn.InstanceNorm3d,\n            torch.nn.LayerNorm,\n            torch.nn.LocalResponseNorm,\n        )\n\n        params: List[Dict[str, Any]] = []\n        memo: Set[torch.nn.parameter.Parameter] = set()\n        for module_name, module in model.named_modules():\n            for module_param_name, value in module.named_parameters(recurse=False):\n                if not value.requires_grad:\n                    continue\n                # Avoid duplicating parameters\n                if value in memo:\n                    continue\n                memo.add(value)\n\n                hyperparams = copy.copy(defaults)\n                if \"backbone\" in module_name:\n                    hyperparams[\"lr\"] = hyperparams[\"lr\"] * cfg.SOLVER.BACKBONE_MULTIPLIER\n                if (\n                    \"relative_position_bias_table\" in module_param_name\n                    or \"absolute_pos_embed\" in module_param_name\n                ):\n                    print(module_param_name)\n                    hyperparams[\"weight_decay\"] = 0.0\n                if isinstance(module, norm_module_types):\n                    hyperparams[\"weight_decay\"] = weight_decay_norm\n                if isinstance(module, torch.nn.Embedding):\n                    hyperparams[\"weight_decay\"] = weight_decay_embed\n                params.append({\"params\": [value], **hyperparams})\n\n        def maybe_add_full_model_gradient_clipping(optim):\n            # detectron2 doesn't have full model gradient clipping now\n            clip_norm_val = cfg.SOLVER.CLIP_GRADIENTS.CLIP_VALUE\n            enable = (\n                cfg.SOLVER.CLIP_GRADIENTS.ENABLED\n                and cfg.SOLVER.CLIP_GRADIENTS.CLIP_TYPE == \"full_model\"\n                and clip_norm_val > 0.0\n            )\n\n            class FullModelGradientClippingOptimizer(optim):\n                def step(self, closure=None):\n                    all_params = itertools.chain(*[x[\"params\"] for x in self.param_groups])\n                    torch.nn.utils.clip_grad_norm_(all_params, clip_norm_val)\n                    super().step(closure=closure)\n\n            return FullModelGradientClippingOptimizer if enable else optim\n\n        optimizer_type = cfg.SOLVER.OPTIMIZER\n        if optimizer_type == \"SGD\":\n            optimizer = maybe_add_full_model_gradient_clipping(torch.optim.SGD)(\n                params, cfg.SOLVER.BASE_LR, momentum=cfg.SOLVER.MOMENTUM\n            )\n        elif optimizer_type == \"ADAMW\":\n            optimizer = maybe_add_full_model_gradient_clipping(torch.optim.AdamW)(\n                params, cfg.SOLVER.BASE_LR\n            )\n        else:\n            raise NotImplementedError(f\"no optimizer type {optimizer_type}\")\n        if not cfg.SOLVER.CLIP_GRADIENTS.CLIP_TYPE == \"full_model\":\n            optimizer = maybe_add_gradient_clipping(cfg, optimizer)\n        return optimizer\n\n    @classmethod\n    def test_with_TTA(cls, cfg, model):\n        logger = logging.getLogger(\"detectron2.trainer\")\n        # In the end of training, run an evaluation with TTA.\n        logger.info(\"Running inference with test-time augmentation ...\")\n        model = SemanticSegmentorWithTTA(cfg, model)\n        evaluators = [\n            cls.build_evaluator(\n                cfg, name, output_folder=os.path.join(cfg.OUTPUT_DIR, \"inference_TTA\")\n            )\n            for name in cfg.DATASETS.TEST\n        ]\n        res = cls.test(cfg, model, evaluators)\n        res = OrderedDict({k + \"_TTA\": v for k, v in res.items()})\n        return res\n\n","metadata":{"execution":{"iopub.status.busy":"2022-09-22T15:03:21.694592Z","iopub.execute_input":"2022-09-22T15:03:21.69501Z","iopub.status.idle":"2022-09-22T15:03:21.718926Z","shell.execute_reply.started":"2022-09-22T15:03:21.694979Z","shell.execute_reply":"2022-09-22T15:03:21.717888Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Load and split and register**","metadata":{}},{"cell_type":"code","source":"%cd ../","metadata":{"execution":{"iopub.status.busy":"2022-09-22T14:36:31.566366Z","iopub.execute_input":"2022-09-22T14:36:31.56679Z","iopub.status.idle":"2022-09-22T14:36:31.57506Z","shell.execute_reply.started":"2022-09-22T14:36:31.566749Z","shell.execute_reply":"2022-09-22T14:36:31.57406Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"\nDatadicts = load_coco_json(cfgDict[\"annotationPath\"],cfgDict[\"newDataPath\"])\n\nskf = StratifiedKFold(n_splits=5, shuffle=True, random_state=cfgDict[\"seed\"])\ny = np.array([int(len(d[\"annotations\"]) > 0) for d in Datadicts])\nsplitIdx = list(skf.split(Datadicts, y))\ntrainIdx, validIdx = splitIdx[0]\nif cfgDict[\"debug\"]:\n    trainIdx = trainIdx[:cfgDict[\"sampleSize\"]]\n    validIdx = validIdx[:cfgDict[\"sampleSize\"]]","metadata":{"execution":{"iopub.status.busy":"2022-09-22T14:39:58.491598Z","iopub.execute_input":"2022-09-22T14:39:58.492077Z","iopub.status.idle":"2022-09-22T14:39:58.630215Z","shell.execute_reply.started":"2022-09-22T14:39:58.492037Z","shell.execute_reply":"2022-09-22T14:39:58.629296Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":"DatasetCatalog.clear()\nMetadataCatalog.clear()\nDatasetCatalog.register(\n        cfgDict[\"trainDataName\"],\n        lambda: [Datadicts[i] for i in trainIdx]\n    )\nDatasetCatalog.register(\n        cfgDict[\"validDataName\"],\n        lambda: [Datadicts[i] for i in validIdx]\n    )\n\nMetadataCatalog.get(cfgDict[\"trainDataName\"]).set(thing_classes=cfgDict[\"thing_classes\"])\nMetadataCatalog.get(cfgDict[\"validDataName\"]).set(thing_classes=cfgDict[\"thing_classes\"])\nmetadata = MetadataCatalog.get(cfgDict[\"trainDataName\"])\ndatasetTrain = DatasetCatalog.get(cfgDict[\"trainDataName\"])","metadata":{"execution":{"iopub.status.busy":"2022-09-22T14:55:14.88251Z","iopub.execute_input":"2022-09-22T14:55:14.883236Z","iopub.status.idle":"2022-09-22T14:55:14.889851Z","shell.execute_reply.started":"2022-09-22T14:55:14.883199Z","shell.execute_reply":"2022-09-22T14:55:14.888918Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"code","source":" cfg = get_cfg()\n    # for poly lr schedule\nadd_deeplab_config(cfg)\nadd_maskformer2_config(cfg)\n\ncfg.merge_from_file(model_zoo.get_config_file(cfgDict[\"modelName\"]))\ncfg.DATASETS.TRAIN = (cfgDict[\"trainDataName\"],)\ncfg.MODEL.DEVICE = cfgDict[\"device\"]\ncfg.INPUT.DATASET_MAPPER_NAME = \"mask_former_instance\"\ncfg.MODEL.MASK_FORMER.TEST.SEMANTIC_ON = False\ncfg.MODEL.MASK_FORMER.TEST.INSTANCE_ON = True\ncfg.MODEL.MASK_FORMER.TEST.PANOPTIC_ON = False\ncfg.OUTPUT_DIR = cfgDict[\"outdir\"]\nif cfgDict[\"splitMode\"] is None:\n    cfg.DATASETS.TEST = ()\nelse:\n    cfg.DATASETS.TEST = (cfgDict[\"validDataName\"],)\n    cfg.TEST.EVAL_PERIOD = cfgDict[\"eval_period\"]\ncfg.MODEL.WEIGHTS = model_zoo.get_checkpoint_url(cfgDict[\"modelName\"])\ncfg.DATALOADER.NUM_WORKERS = cfgDict[\"num_workers\"]\ncfg.SOLVER.IMS_PER_BATCH = cfgDict[\"ims_per_batch\"]\ncfg.SOLVER.LR_SCHEDULER_NAME = cfgDict[\"lr_scheduler_name\"]\ncfg.SOLVER.BASE_LR = cfgDict[\"base_lr\"]\ncfg.SOLVER.MAX_ITER = cfgDict[\"iter\"]\ncfg.SOLVER.CHECKPOINT_PERIOD = cfgDict[\"checkpoint_period\"]\ncfg.MODEL.ROI_HEADS.BATCH_SIZE_PER_IMAGE = cfgDict[\"roi_batch_size_per_image\"]\ncfg.MODEL.ROI_HEADS.NUM_CLASSES = len(set(metadata.get(\"thing_classes\")))\ncfg.INPUT.MASK_FORMAT = cfgDict[\"mask_format\"]\ncfg.MODEL.ROI_HEADS.SCORE_THRESH_TEST = cfgDict[\"score_thresh_test\"]\n\ncfg.freeze()\n\n# Setup logger for \"mask_former\" module\nsetup_logger(output=cfg.OUTPUT_DIR, distributed_rank=comm.get_rank(), name=\"mask2former\")","metadata":{"execution":{"iopub.status.busy":"2022-09-22T15:03:31.71038Z","iopub.execute_input":"2022-09-22T15:03:31.710777Z","iopub.status.idle":"2022-09-22T15:03:31.741229Z","shell.execute_reply.started":"2022-09-22T15:03:31.710745Z","shell.execute_reply":"2022-09-22T15:03:31.740037Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Train**","metadata":{}},{"cell_type":"code","source":"trainer = COCOTrainer(cfg)\ntrainer.resume_or_load(resume=False)\ntrainer.train()","metadata":{"execution":{"iopub.status.busy":"2022-09-22T15:05:41.02628Z","iopub.execute_input":"2022-09-22T15:05:41.026701Z","iopub.status.idle":"2022-09-22T15:06:05.384873Z","shell.execute_reply.started":"2022-09-22T15:05:41.026647Z","shell.execute_reply":"2022-09-22T15:06:05.38118Z"},"trusted":true},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Evaluation**","metadata":{}},{"cell_type":"code","source":"dfMetrics = pd.read_json(os.path.join(cfgDict[\"outdir\"],\"metrics.json\"), orient=\"records\", lines=True)\ndfMetrics = dfMetrics.sort_values(\"iteration\")\ndfMetrics.head()\n\ndfTrainLoss = dfMetrics[~dfMetrics[\"total_loss\"].isna()]\nplt.plot(dfTrainLoss[\"iteration\"], dfTrainLoss[\"total_loss\"], c=\"C0\", label=\"train\")\nif \"validation_loss\" in dfMetrics.columns:\n    dfValidLoss = dfMetrics[~dfMetrics[\"validation_loss\"].isna()]\n    plt.plot(dfValidLoss[\"iteration\"], dfValidLoss[\"validation_loss\"], c=\"C1\", label=\"validation\")\n\nplt.legend()\nplt.title(\"Loss curve\")\nplt.xlabel(\"Iteration\")\nplt.show()","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**predict**","metadata":{}},{"cell_type":"code","source":"# Same cfg from trainer and use the final model output to initialize the predictor\ncfg.MODEL.WEIGHTS = os.path.join(cfgDict[\"outdir\"],\"model_final.pth\")\npredictor = DefaultPredictor(cfg)\n\nfor d in datasetTrain:\n    if len(d[\"annotations\"])>0:\n        break\nim = cv2.imread(d[\"file_name\"])\nif predictor.input_format == \"RGB\":\n    im = im[:, :, ::-1]\nheight, width = im.shape[:2]\nimage = torch.as_tensor(im.astype(\"float32\").transpose(2, 0, 1))\ninputs = [{\"image\": image, \"height\": height, \"width\": width}]\noutputs = predictor.model(inputs)\noutput = outputs[0]\n\nvisualizer = Visualizer(im,metadata=metadata, scale=1, instance_mode=ColorMode.IMAGE_BW)\nout = visualizer.draw_instance_predictions(output[\"instances\"].to(\"cpu\"))\nImage.fromarray(out.get_image()[:, :, ::-1])","metadata":{},"execution_count":null,"outputs":[]},{"cell_type":"markdown","source":"**Submit**","metadata":{}},{"cell_type":"code","source":"enc_rle = mask2rle(mask)\n\ntest_df = pd.DataFrame(enc_rle)\ntest_df.to_csv('submission.csv', index=False)","metadata":{},"execution_count":null,"outputs":[]}]}