{"metadata":{"kernelspec":{"language":"python","display_name":"Python 3","name":"python3"},"language_info":{"name":"python","version":"3.10.14","mimetype":"text/x-python","codemirror_mode":{"name":"ipython","version":3},"pygments_lexer":"ipython3","nbconvert_exporter":"python","file_extension":".py"},"kaggle":{"accelerator":"nvidiaTeslaT4","dataSources":[{"sourceId":7327,"databundleVersionId":861871,"sourceType":"competition"}],"dockerImageVersionId":30805,"isInternetEnabled":true,"language":"python","sourceType":"notebook","isGpuEnabled":true}},"nbformat_minor":4,"nbformat":4,"cells":[{"cell_type":"code","source":"import pandas as pd\nimport numpy as np\nimport torch","metadata":{"_uuid":"8f2839f25d086af736a60e9eeb907d3b93b6e0e5","_cell_guid":"b1076dfc-b9ad-4769-8c92-a6c4dae69d19","trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:30.445797Z","iopub.execute_input":"2024-12-09T13:09:30.446049Z","iopub.status.idle":"2024-12-09T13:09:34.095064Z","shell.execute_reply.started":"2024-12-09T13:09:30.446021Z","shell.execute_reply":"2024-12-09T13:09:34.094357Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"#using GPU for faster training\ndevice=torch.device('cuda:0' if torch.cuda.is_available() else 'cpu')\nuse_cuda=torch.cuda.is_available()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.096766Z","iopub.execute_input":"2024-12-09T13:09:34.097474Z","iopub.status.idle":"2024-12-09T13:09:34.170958Z","shell.execute_reply.started":"2024-12-09T13:09:34.097431Z","shell.execute_reply":"2024-12-09T13:09:34.169849Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Read csv","metadata":{}},{"cell_type":"code","source":"# read the csv\nlabels = pd.read_csv(\"/kaggle/input/dog-breed-identification/labels.csv\")\nsample_submission = pd.read_csv(\"/kaggle/input/dog-breed-identification/sample_submission.csv\")","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.172267Z","iopub.execute_input":"2024-12-09T13:09:34.172706Z","iopub.status.idle":"2024-12-09T13:09:34.779185Z","shell.execute_reply.started":"2024-12-09T13:09:34.172637Z","shell.execute_reply":"2024-12-09T13:09:34.778299Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.781805Z","iopub.execute_input":"2024-12-09T13:09:34.782489Z","iopub.status.idle":"2024-12-09T13:09:34.799748Z","shell.execute_reply.started":"2024-12-09T13:09:34.782441Z","shell.execute_reply":"2024-12-09T13:09:34.798965Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"sample_submission.head()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.800750Z","iopub.execute_input":"2024-12-09T13:09:34.801064Z","iopub.status.idle":"2024-12-09T13:09:34.824295Z","shell.execute_reply.started":"2024-12-09T13:09:34.801030Z","shell.execute_reply":"2024-12-09T13:09:34.823462Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# EDA","metadata":{}},{"cell_type":"code","source":"labels.info()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.825367Z","iopub.execute_input":"2024-12-09T13:09:34.825655Z","iopub.status.idle":"2024-12-09T13:09:34.847256Z","shell.execute_reply.started":"2024-12-09T13:09:34.825628Z","shell.execute_reply":"2024-12-09T13:09:34.846476Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"sample_submission.info()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.848229Z","iopub.execute_input":"2024-12-09T13:09:34.848478Z","iopub.status.idle":"2024-12-09T13:09:34.864019Z","shell.execute_reply.started":"2024-12-09T13:09:34.848451Z","shell.execute_reply":"2024-12-09T13:09:34.863352Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels[\"breed\"].describe()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.864980Z","iopub.execute_input":"2024-12-09T13:09:34.865226Z","iopub.status.idle":"2024-12-09T13:09:34.873168Z","shell.execute_reply.started":"2024-12-09T13:09:34.865190Z","shell.execute_reply":"2024-12-09T13:09:34.872303Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels[\"breed\"].value_counts()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.874131Z","iopub.execute_input":"2024-12-09T13:09:34.874512Z","iopub.status.idle":"2024-12-09T13:09:34.883589Z","shell.execute_reply.started":"2024-12-09T13:09:34.874473Z","shell.execute_reply":"2024-12-09T13:09:34.882710Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"**NOTE**:\n+ There are 120 breeds\n+ Around 10k for train and 10k for test","metadata":{}},{"cell_type":"code","source":"import matplotlib.pyplot as plt\nimport seaborn as sns\nplt.figure(figsize=(30,20))\nsns.countplot(y=\"breed\",data=labels,palette=\"Set1\") # using palette set1 for better visualization\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:34.887761Z","iopub.execute_input":"2024-12-09T13:09:34.888014Z","iopub.status.idle":"2024-12-09T13:09:36.678457Z","shell.execute_reply.started":"2024-12-09T13:09:34.887990Z","shell.execute_reply":"2024-12-09T13:09:36.677614Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## Visualize train image","metadata":{}},{"cell_type":"code","source":"import matplotlib.pyplot as plt\nimport random\nfrom PIL import Image\nimport pandas as pd\ndf = labels\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:36.679715Z","iopub.execute_input":"2024-12-09T13:09:36.680541Z","iopub.status.idle":"2024-12-09T13:09:36.684757Z","shell.execute_reply.started":"2024-12-09T13:09:36.680496Z","shell.execute_reply":"2024-12-09T13:09:36.683913Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"image_dir = \"/kaggle/input/dog-breed-identification/train/\"\n\ndf['image_path'] = df['id'].apply(lambda x: f\"{image_dir}{x}.jpg\")\n\nrandom_samples = df.sample(25,replace=True)\n\nfig, axes = plt.subplots(5, 5, figsize=(15, 15))\naxes = axes.flatten()\n\nfor i, (index, row) in enumerate(random_samples.iterrows()):\n    img = Image.open(row['image_path'])\n    axes[i].imshow(img)\n    axes[i].set_title(row['breed'], fontsize=12, loc='center')\n    axes[i].axis('off')\n\nplt.tight_layout()\nplt.show()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:36.685717Z","iopub.execute_input":"2024-12-09T13:09:36.685967Z","iopub.status.idle":"2024-12-09T13:09:39.724940Z","shell.execute_reply.started":"2024-12-09T13:09:36.685942Z","shell.execute_reply":"2024-12-09T13:09:39.723962Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"df[\"image_path\"][0]","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:39.726139Z","iopub.execute_input":"2024-12-09T13:09:39.726464Z","iopub.status.idle":"2024-12-09T13:09:39.733483Z","shell.execute_reply.started":"2024-12-09T13:09:39.726424Z","shell.execute_reply":"2024-12-09T13:09:39.732723Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"breed=list(df[\"breed\"].value_counts().keys())","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:39.734490Z","iopub.execute_input":"2024-12-09T13:09:39.734789Z","iopub.status.idle":"2024-12-09T13:09:39.744901Z","shell.execute_reply.started":"2024-12-09T13:09:39.734762Z","shell.execute_reply":"2024-12-09T13:09:39.743924Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"np.random.seed(42)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:39.746032Z","iopub.execute_input":"2024-12-09T13:09:39.746318Z","iopub.status.idle":"2024-12-09T13:09:39.751617Z","shell.execute_reply.started":"2024-12-09T13:09:39.746284Z","shell.execute_reply":"2024-12-09T13:09:39.750804Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels.groupby('breed').count().sort_values(by='id',ascending=False)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:39.752596Z","iopub.execute_input":"2024-12-09T13:09:39.752912Z","iopub.status.idle":"2024-12-09T13:09:39.767427Z","shell.execute_reply.started":"2024-12-09T13:09:39.752875Z","shell.execute_reply":"2024-12-09T13:09:39.766721Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Resnet","metadata":{"execution":{"iopub.status.busy":"2024-12-09T07:34:44.480563Z","iopub.execute_input":"2024-12-09T07:34:44.480942Z","iopub.status.idle":"2024-12-09T07:34:44.487937Z","shell.execute_reply.started":"2024-12-09T07:34:44.480912Z","shell.execute_reply":"2024-12-09T07:34:44.486918Z"}}},{"cell_type":"markdown","source":"## Preprocess","metadata":{}},{"cell_type":"code","source":"from torchvision import transforms","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:39.768363Z","iopub.execute_input":"2024-12-09T13:09:39.768625Z","iopub.status.idle":"2024-12-09T13:09:40.767655Z","shell.execute_reply.started":"2024-12-09T13:09:39.768599Z","shell.execute_reply":"2024-12-09T13:09:40.766981Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"#Resizing images to fit Resnet18 architecture\ntrain_trasforms=transforms.Compose([\n    transforms.Resize((224, 224)),\n    transforms.RandomHorizontalFlip(p=0.2),\n    transforms.RandomVerticalFlip(p=0.2),\n    transforms.ColorJitter(brightness=0.2, contrast=0.2, saturation=0.2, hue=0.1),  # Apply color jitter \n    transforms.ToTensor(),\n    transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])] # This is from the original paper\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.768757Z","iopub.execute_input":"2024-12-09T13:09:40.769264Z","iopub.status.idle":"2024-12-09T13:09:40.774711Z","shell.execute_reply.started":"2024-12-09T13:09:40.769217Z","shell.execute_reply":"2024-12-09T13:09:40.773710Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"**Note**: \n+ Why resize to (244,244) and normalize with that mean and std\n    + This is because ResNet is train on ImageNet which has 244,244 as standard\n    +  The ResNet model was trained on images that were normalized using specific mean and standard deviation values for each color channel (RGB).\n+ What is ColorJitter\n    + brightness=0.2: Randomly changes the brightness of the image. The factor (0.2 in this case) defines how much the brightness can vary. It means that the image's brightness can vary by ±20% of its original value.\n    + contrast=0.2: Randomly adjusts the contrast of the image. Similar to brightness, the contrast will vary by ±20%. Contrast refers to the difference in luminance or color that makes an object distinguishable from the background.\n    + saturation=0.2: Randomly adjusts the saturation of the image, which refers to the intensity of the colors. A saturation value of 0.2 means the colors can change by ±20% from their original saturation, making the image either more or less vibrant.\n    + hue=0.1: Randomly shifts the hue of the image, which is the actual color (red, blue, green, etc.). The hue value of 0.1 means that the hue can change by ±10% of the color wheel. This will make the colors of the image shift across different color ranges.","metadata":{}},{"cell_type":"code","source":"from sklearn.preprocessing import LabelEncoder\nencoder = LabelEncoder()","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.776106Z","iopub.execute_input":"2024-12-09T13:09:40.776358Z","iopub.status.idle":"2024-12-09T13:09:40.833129Z","shell.execute_reply.started":"2024-12-09T13:09:40.776334Z","shell.execute_reply":"2024-12-09T13:09:40.832322Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels['breed']=encoder.fit_transform(labels['breed'])","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.834191Z","iopub.execute_input":"2024-12-09T13:09:40.834570Z","iopub.status.idle":"2024-12-09T13:09:40.841265Z","shell.execute_reply.started":"2024-12-09T13:09:40.834521Z","shell.execute_reply":"2024-12-09T13:09:40.840353Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"labels['breed'] ","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.842369Z","iopub.execute_input":"2024-12-09T13:09:40.843181Z","iopub.status.idle":"2024-12-09T13:09:40.852116Z","shell.execute_reply.started":"2024-12-09T13:09:40.843154Z","shell.execute_reply":"2024-12-09T13:09:40.851289Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# stratified train val split\nfrom sklearn.model_selection import train_test_split\nX_train, X_val, y_train, y_val = train_test_split(labels,labels['breed'],test_size=0.2,random_state=42,stratify=labels[\"breed\"])","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.853147Z","iopub.execute_input":"2024-12-09T13:09:40.853417Z","iopub.status.idle":"2024-12-09T13:09:40.936256Z","shell.execute_reply.started":"2024-12-09T13:09:40.853393Z","shell.execute_reply":"2024-12-09T13:09:40.935550Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"y_train","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.937261Z","iopub.execute_input":"2024-12-09T13:09:40.937615Z","iopub.status.idle":"2024-12-09T13:09:40.943881Z","shell.execute_reply.started":"2024-12-09T13:09:40.937574Z","shell.execute_reply":"2024-12-09T13:09:40.943036Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"X_train=pd.DataFrame(X_train)\ny_train=pd.DataFrame(y_train)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.945384Z","iopub.execute_input":"2024-12-09T13:09:40.945878Z","iopub.status.idle":"2024-12-09T13:09:40.953086Z","shell.execute_reply.started":"2024-12-09T13:09:40.945837Z","shell.execute_reply":"2024-12-09T13:09:40.952371Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"## Dataset","metadata":{}},{"cell_type":"code","source":"from torch.utils.data import Dataset, DataLoader","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.954113Z","iopub.execute_input":"2024-12-09T13:09:40.954418Z","iopub.status.idle":"2024-12-09T13:09:40.961827Z","shell.execute_reply.started":"2024-12-09T13:09:40.954390Z","shell.execute_reply":"2024-12-09T13:09:40.961015Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"class DogBreedDataset(Dataset):\n    def __init__(self,root_dir=\"/kaggle/input/dog-breed-identification/train\",transforms=None,labels=None):\n        self.root_dir = root_dir\n        self.transforms = transforms \n        self.labels = labels\n        \n    def __len__(self):\n        return len(self.labels)\n        \n    def __getitem__(self,idx):\n        img_name=self.labels[idx]['id'] \n        img_path=os.path.join(self.root_dir,img_name+'.jpg') \n        image=Image.open(img_path)\n        label=self.labels[idx]['breed']\n        if self.transforms: \n            image=self.transforms(image)\n        return image,label\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.962947Z","iopub.execute_input":"2024-12-09T13:09:40.963503Z","iopub.status.idle":"2024-12-09T13:09:40.972941Z","shell.execute_reply.started":"2024-12-09T13:09:40.963439Z","shell.execute_reply":"2024-12-09T13:09:40.972162Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"train_dataset=DogBreedDataset('/kaggle/input/dog-breed-identification/train',\n                               transforms=train_trasforms,\n                               labels=X_train.to_dict('records'))","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:40.973979Z","iopub.execute_input":"2024-12-09T13:09:40.974314Z","iopub.status.idle":"2024-12-09T13:09:40.999998Z","shell.execute_reply.started":"2024-12-09T13:09:40.974267Z","shell.execute_reply":"2024-12-09T13:09:40.999405Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"**Note**:\n+ X_train.to_dict('records') change the X from df to map","metadata":{"execution":{"iopub.status.busy":"2024-12-09T09:18:32.431010Z","iopub.execute_input":"2024-12-09T09:18:32.431809Z","iopub.status.idle":"2024-12-09T09:18:32.438542Z","shell.execute_reply.started":"2024-12-09T09:18:32.431769Z","shell.execute_reply":"2024-12-09T09:18:32.437064Z"}}},{"cell_type":"code","source":"train_dataloader=DataLoader(train_dataset, batch_size=32, shuffle=True)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:09:41.003258Z","iopub.execute_input":"2024-12-09T13:09:41.003498Z","iopub.status.idle":"2024-12-09T13:09:41.007601Z","shell.execute_reply.started":"2024-12-09T13:09:41.003473Z","shell.execute_reply":"2024-12-09T13:09:41.006650Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"val_trasforms=transforms.Compose([\n    transforms.Resize((224, 224)),\n    transforms.ToTensor(),\n    transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])]\n)\nval_dataset=DogBreedDataset('/kaggle/input/dog-breed-identification/train',\n                               transforms=val_trasforms,\n                               labels=X_val.to_dict('records'))","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:35.228466Z","iopub.execute_input":"2024-12-09T13:10:35.228837Z","iopub.status.idle":"2024-12-09T13:10:35.398385Z","shell.execute_reply.started":"2024-12-09T13:10:35.228806Z","shell.execute_reply":"2024-12-09T13:10:35.397179Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"val_dataloader=DataLoader(val_dataset, batch_size=32, shuffle=True)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:45.216043Z","iopub.execute_input":"2024-12-09T13:10:45.216393Z","iopub.status.idle":"2024-12-09T13:10:45.220827Z","shell.execute_reply.started":"2024-12-09T13:10:45.216359Z","shell.execute_reply":"2024-12-09T13:10:45.219856Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Training","metadata":{}},{"cell_type":"code","source":"import torchvision.models as models","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:48.284589Z","iopub.execute_input":"2024-12-09T13:10:48.284942Z","iopub.status.idle":"2024-12-09T13:10:48.289013Z","shell.execute_reply.started":"2024-12-09T13:10:48.284911Z","shell.execute_reply":"2024-12-09T13:10:48.288147Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"using resnet18 from models of torchvision","metadata":{}},{"cell_type":"code","source":"net = models.resnet18(pretrained=True)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:49.506783Z","iopub.execute_input":"2024-12-09T13:10:49.507110Z","iopub.status.idle":"2024-12-09T13:10:50.191062Z","shell.execute_reply.started":"2024-12-09T13:10:49.507081Z","shell.execute_reply":"2024-12-09T13:10:50.190151Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"num_classes=len(labels['breed'].unique())","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:52.356414Z","iopub.execute_input":"2024-12-09T13:10:52.357092Z","iopub.status.idle":"2024-12-09T13:10:52.361376Z","shell.execute_reply.started":"2024-12-09T13:10:52.357057Z","shell.execute_reply":"2024-12-09T13:10:52.360480Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"import torch.nn as nn\n# change the last layer\nnet.fc = nn.Sequential(\n    nn.Dropout(0.4),  # Dropout with a probability of 0.4\n    nn.Linear(net.fc.in_features, 512),\n    nn.BatchNorm1d(512),\n    nn.LeakyReLU(negative_slope=0.01),\n    nn.Linear(512,num_classes))\nnet = net.cuda() if use_cuda else net # move net to cuda","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:53.679790Z","iopub.execute_input":"2024-12-09T13:10:53.680120Z","iopub.status.idle":"2024-12-09T13:10:53.884169Z","shell.execute_reply.started":"2024-12-09T13:10:53.680092Z","shell.execute_reply":"2024-12-09T13:10:53.883448Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"criterion=nn.CrossEntropyLoss()\nlearning_rate=0.0001\noptimizer = torch.optim.AdamW(net.parameters(), lr=learning_rate) # train the whole model\n# ~100M params","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:57.158480Z","iopub.execute_input":"2024-12-09T13:10:57.158817Z","iopub.status.idle":"2024-12-09T13:10:57.163713Z","shell.execute_reply.started":"2024-12-09T13:10:57.158786Z","shell.execute_reply":"2024-12-09T13:10:57.162750Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"from torch.optim.lr_scheduler import StepLR\n\nscheduler = StepLR(optimizer, step_size=7, gamma=0.1)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:10:58.934136Z","iopub.execute_input":"2024-12-09T13:10:58.934812Z","iopub.status.idle":"2024-12-09T13:10:58.938872Z","shell.execute_reply.started":"2024-12-09T13:10:58.934774Z","shell.execute_reply":"2024-12-09T13:10:58.937921Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"This scheduler adjusts the learning rate by a factor (gamma) at regular intervals (defined by step_size).","metadata":{}},{"cell_type":"code","source":"import os\ntorch.manual_seed(42)# fixing the seed\n\ntrain_losses = [] #to save train losses\nval_losses = [] #to save test losses\n\nepochs = 20\nfor epoch in range(epochs):\n    # Training\n    net.train() # in training mode\n    train_loss = 0.0\n    for features, target in train_dataloader: #iterate over the train dataloader\n        optimizer.zero_grad() #to set gradient to zero at the begnining of each epoch\n        features = features.to(device).double()\n        target = target.to(device)\n        outputs = net(features.float()) #calculating outputs from the features\n        loss = criterion(outputs, target) #calculate loss\n        loss.backward() \n        optimizer.step()\n        train_loss += loss.item() * features.size(0)\n    train_loss /= len(train_dataloader.dataset)\n    train_losses.append(train_loss)\n\n    # Evaluation\n    net.eval()\n    val_loss = 0.0\n    correct = 0\n    total = 0\n    with torch.no_grad():\n        for features_t, target_t in val_dataloader:\n            features_t = features_t.to(device).double()\n            target_t = target_t.to(device)\n            outputs_t = net(features_t.float())\n            loss_t = criterion(outputs_t, target_t)\n            val_loss += loss_t.item() * features_t.size(0)  # Use features_t.size(0) for val_loss accumulation\n            _, pred_t = torch.max(outputs_t, 1)\n            total += target_t.size(0)  # Use target_t.size(0) to update total\n            correct += (pred_t == target_t).sum().item()\n    val_loss /= len(val_dataloader.dataset)\n    val_losses.append(val_loss)\n    scheduler.step()\n    \n    if epoch % 1 == 0:\n        print(f'Epoch {epoch+1}/{epochs}, Train Loss: {train_loss:.4f}, Test Loss: {val_loss:.4f}, Test Accuracy: {(100 * correct / total):.2f}%')","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:11:57.180790Z","iopub.execute_input":"2024-12-09T13:11:57.181726Z","iopub.status.idle":"2024-12-09T13:52:32.940459Z","shell.execute_reply.started":"2024-12-09T13:11:57.181656Z","shell.execute_reply":"2024-12-09T13:52:32.939514Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"**Note**:\n+ Why multiply features.size(0):\n    + The loss (loss.item()) is calculated for each batch of data in the training set.\n    + The loss in this case is the average loss for that particular batch. Specifically, it is the mean loss across all the samples in the batch.  ","metadata":{}},{"cell_type":"code","source":"import matplotlib.pyplot as plt\n\n# Assuming you have trainlosses and val_losses lists\nepochs = list(range(1, 21))  # 20 epochs\n# Plotting\nplt.figure(figsize=(10, 6))\nplt.plot(epochs, train_losses, label='Training Loss', color='blue', marker='o')\nplt.plot(epochs, val_losses, label='Validation Loss', color='orange', marker='o')\n\n# Adding labels and title\nplt.xlabel('Epochs')\nplt.ylabel('Loss')\nplt.title('Training and Validation Loss Over Time')\nplt.legend()\n\n# Show the plot\nplt.grid(True)\nplt.show()\n","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T13:54:29.444500Z","iopub.execute_input":"2024-12-09T13:54:29.444854Z","iopub.status.idle":"2024-12-09T13:54:29.735242Z","shell.execute_reply.started":"2024-12-09T13:54:29.444824Z","shell.execute_reply":"2024-12-09T13:54:29.734378Z"}},"outputs":[],"execution_count":null},{"cell_type":"markdown","source":"# Evaluation","metadata":{}},{"cell_type":"code","source":"#custom class to read and transform the test data \nclass Dog_Breed_Dataset_test(Dataset):\n    def __init__ (self, root_dir,transform=None):\n        self.root_dir=root_dir # directory of images\n        self.transforms=transform #transformation\n        self.image_names=[f.split('.')[0] for f in os.listdir(root_dir)] #image name is the first element after splitting on \".\"\n    def __len__(self):\n        return len(self.image_names)\n    def __getitem__(self,idx):\n        img_name=self.image_names[idx] #read images names from csv\n        img_path=os.path.join(self.root_dir,img_name+'.jpg') # construct image path from the csv and directory\n        image=Image.open(img_path)\n    \n        if self.transforms: # if there is a transformation , apply it to data and then return image and its name\n            image=self.transforms(image)\n        return image,img_name","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:04:10.572968Z","iopub.execute_input":"2024-12-09T14:04:10.573716Z","iopub.status.idle":"2024-12-09T14:04:10.579466Z","shell.execute_reply.started":"2024-12-09T14:04:10.573652Z","shell.execute_reply":"2024-12-09T14:04:10.578497Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"test_transforms = transforms.Compose([\n    transforms.Resize((224, 224)),\n    transforms.ToTensor(),\n    transforms.Normalize(mean=[0.485, 0.456, 0.406], std=[0.229, 0.224, 0.225])]\n)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:04:13.210350Z","iopub.execute_input":"2024-12-09T14:04:13.210924Z","iopub.status.idle":"2024-12-09T14:04:13.216070Z","shell.execute_reply.started":"2024-12-09T14:04:13.210885Z","shell.execute_reply":"2024-12-09T14:04:13.214913Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"kaggle_test=Dog_Breed_Dataset_test(root_dir='/kaggle/input/dog-breed-identification/test',\n                                  transform=test_transforms)\n\n#kaggla test data loader\nkaggle_test_dataloader=DataLoader(kaggle_test,batch_size=32,shuffle=False)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:04:14.440576Z","iopub.execute_input":"2024-12-09T14:04:14.441050Z","iopub.status.idle":"2024-12-09T14:04:14.452370Z","shell.execute_reply.started":"2024-12-09T14:04:14.441015Z","shell.execute_reply":"2024-12-09T14:04:14.451711Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"dog_breeds = encoder.classes_","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:05:44.625563Z","iopub.execute_input":"2024-12-09T14:05:44.625909Z","iopub.status.idle":"2024-12-09T14:05:44.630327Z","shell.execute_reply.started":"2024-12-09T14:05:44.625880Z","shell.execute_reply":"2024-12-09T14:05:44.629410Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"# import torch\nimport torch.nn.functional as F\n\n# Make sure the model is in evaluation mode\nnet.eval()\n\n# List to store all predictions\nall_predictions = []\n\n# Disable gradient calculations\nwith torch.no_grad():\n    for features_t , img_names in kaggle_test_dataloader:\n        features_t = features_t.to(device).double()  # Move features to the appropriate device and ensure they are double type\n\n        # Get model predictions\n        outputs_t = net(features_t.float())  # Get the raw outputs from the model\n        \n        # Convert raw outputs to probabilities using softmax\n        probabilities = F.softmax(outputs_t, dim=1)\n        \n        # Append probabilities to the list of all predictions\n       # Extract probabilities for each class for each image\n        for i in range(len(img_names)):\n            probabilities_for_image = probabilities[i].cpu().numpy()\n            for class_idx, prob in enumerate(probabilities_for_image):\n                class_name = dog_breeds[class_idx]  # Assuming class_names is a list containing the class names\n                all_predictions.append({'class_name': class_name, 'probability': prob, 'image_name': img_names[i]})","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:05:48.595092Z","iopub.execute_input":"2024-12-09T14:05:48.595440Z","iopub.status.idle":"2024-12-09T14:08:03.796976Z","shell.execute_reply.started":"2024-12-09T14:05:48.595407Z","shell.execute_reply":"2024-12-09T14:08:03.795958Z"}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"all_predictions","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:08:52.682863Z","iopub.execute_input":"2024-12-09T14:08:52.683536Z","iopub.status.idle":"2024-12-09T14:08:52.761020Z","shell.execute_reply.started":"2024-12-09T14:08:52.683498Z","shell.execute_reply":"2024-12-09T14:08:52.760037Z"},"collapsed":true,"jupyter":{"outputs_hidden":true}},"outputs":[],"execution_count":null},{"cell_type":"code","source":"#preparing submissions file\nall_predictions_df = pd.DataFrame.from_records(all_predictions)\nsubmissions = all_predictions_df.pivot(index='image_name', columns='class_name', values='probability')\n\n# Reset index to make 'image_name' a regular column instead of index\nsubmissions.reset_index(inplace=True)\n\n#writing the csv file for predictions\nsubmissions=submissions.rename(columns={'image_name':'id'})\nsubmissions.to_csv('submission.csv',index=False)","metadata":{"trusted":true,"execution":{"iopub.status.busy":"2024-12-09T14:09:22.624894Z","iopub.execute_input":"2024-12-09T14:09:22.625603Z","iopub.status.idle":"2024-12-09T14:09:25.099039Z","shell.execute_reply.started":"2024-12-09T14:09:22.625569Z","shell.execute_reply":"2024-12-09T14:09:25.098364Z"}},"outputs":[],"execution_count":null}]}