{"cells":[{"metadata":{"trusted":true},"cell_type":"code","source":"import numpy as np, pandas as pd","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"# Raster Size Ensembling\n\n**This notebook serves as 1) a simple demo showing how to submit multi-mode submissions and 2) to talk about ensembling raster sizes. As you can read about [here](https://www.kaggle.com/c/lyft-motion-prediction-autonomous-vehicles/discussion/178323) `raster_size` parameter changes how much of the scene the rasterized image shows: a larger raster size increases the region that the model sees during training. As such, it is an important hyperparameter. Does our model need to see agents from very far away? Or should we force it to focus on agents near it? Why don't we do both? We can train models on different raster sizes and then ensemble their predictions via the multi-mode submission ability of this competition**\n\n\n# Notes\n\n**All the pre-trained models are saved [here](https://www.kaggle.com/tuckerarrants/lyftpretrainedmodels), so you can just add this dataset to a Kaggle kernel and run inference with it, like I do [here](https://www.kaggle.com/tuckerarrants/lyft-inference-resnet18) to get the different raster size predictions that I am blending. You could also just download the output of this kernel if you want the prediction `.csv`.**\n\n**Current LB scores:**\n* (300 raster_size, pixel_size .5, 10 history_num_frames, 75000 steps ) - 129.99\n* (450 raster_size, pixel_size .5, 10 history_num_frames, 25000 steps ) - 135.899\n* (600 raster_size, pixel_size .2, 10 history_num_frames, 75000 steps ) - 121.555\n\n\n**Defer to Peter's notebook [here](https://www.kaggle.com/pestipeti/pytorch-baseline-train) for further training specific details**","execution_count":null},{"metadata":{"_uuid":"d629ff2d2480ee46fbb7e2d37f6b5fab8052498a","_cell_guid":"79c7e3d0-c299-4dcb-8224-4455121ee9b0","trusted":true},"cell_type":"code","source":"#steal multi mode template from sample sub\nmulti_mode_submission = pd.read_csv('../input/lyft-motion-prediction-autonomous-vehicles/multi_mode_sample_submission.csv')\n\n#so we can set confidence intervals easily\ncols = list(multi_mode_submission.columns)\nconfs = cols[2:5]\nconf0 = cols[5:105]\nconf1 = cols[105:205]\nconf2 = cols[205:305]","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"sub0 = pd.read_csv('../input/lyftsubmissions/submission_r300_px.5_74999.csv')\nsub1 = pd.read_csv('../input/lyftsubmissions/submission_r450_px.5_24999.csv')\nsub2 = pd.read_csv('../input/lyftsubmissions/submission_r600_px.2_74999.csv')","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"**You can probably get better scores by changing the confidence intervals of the different submissions, or by training with your own raster size and ensembling that prediction in here to continue the experiment**","execution_count":null},{"metadata":{"trusted":true},"cell_type":"code","source":"#change this to experiment with different ensemble weights\nmulti_mode_submission[confs] = [.3,.2,.5]\n\nmulti_mode_submission[conf0] = sub0[conf0]\nmulti_mode_submission[conf1] = sub1[conf0]\nmulti_mode_submission[conf2] = sub2[conf0]","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#sanity check\nmulti_mode_submission[conf0].head()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#another sanity check\nmulti_mode_submission[conf1].head()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#okay last one\nmulti_mode_submission[conf2].head()","execution_count":null,"outputs":[]},{"metadata":{"trusted":true},"cell_type":"code","source":"#save to .csv for submission\nmulti_mode_submission.to_csv('submission.csv', index = False, float_format='%.6g') ","execution_count":null,"outputs":[]},{"metadata":{},"cell_type":"markdown","source":"# Model Architeture (For Reference)\n\n**Below is the architeture of the model that was trained on different raster sizes:**","execution_count":null},{"metadata":{"trusted":true},"cell_type":"code","source":"import torch.nn as nn\nfrom typing import Dict\n\nclass LyftModel(nn.Module):\n    \n    def __init__(self, cfg: Dict):\n        super().__init__()\n        \n        self.backbone = resnet18(pretrained=False)\n        \n        num_history_channels = (cfg[\"model_params\"][\"history_num_frames\"] + 1) * 2\n        num_in_channels = 3 + num_history_channels\n\n        self.backbone.conv1 = nn.Conv2d(\n            num_in_channels,\n            self.backbone.conv1.out_channels,\n            kernel_size=self.backbone.conv1.kernel_size,\n            stride=self.backbone.conv1.stride,\n            padding=self.backbone.conv1.padding,\n            bias=False,\n        )\n        \n        num_targets = 2 * cfg[\"model_params\"][\"future_num_frames\"]\n\n        self.head = nn.Sequential(\n            nn.Linear(in_features=512, out_features=4096),\n        )\n\n        self.logit = nn.Linear(4096, out_features=num_targets)\n        \n    def forward(self, x):\n        x = self.backbone.conv1(x)\n        x = self.backbone.bn1(x)\n        x = self.backbone.relu(x)\n        x = self.backbone.maxpool(x)\n\n        x = self.backbone.layer1(x)\n        x = self.backbone.layer2(x)\n        x = self.backbone.layer3(x)\n        x = self.backbone.layer4(x)\n\n        x = self.backbone.avgpool(x)\n        x = torch.flatten(x, 1)\n        \n        x = self.head(x)\n        x = self.logit(x)\n        \n        return x","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}