Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import os
- from torchvision import datasets
- import torchvision
- ### TODO: Write data loaders for training, validation, and test sets
- ## Specify appropriate transforms, and batch_sizes
- data_dir = '/data/dog_images'
- train_dir = data_dir + '/train'
- valid_dir = data_dir + '/valid'
- test_dir = data_dir + '/test'
- data_transforms={
- 'train_transform':transforms.Compose([transforms.Resize(224),
- transforms.RandomRotation(30),
- #transforms.RandomResizedCrop(256),
- transforms.RandomHorizontalFlip(),
- transforms.ToTensor(),
- transforms.Normalize([0.485, 0.456, 0.406],
- [0.229, 0.224, 0.225])]),
- 'valid_transform':transforms.Compose([transforms.Resize(256),
- transforms.CenterCrop(256),
- transforms.ToTensor(),
- transforms.Normalize([0.485, 0.456, 0.406],
- [0.229, 0.224, 0.225])]),
- 'test_transform':transforms.Compose([transforms.Resize(256),
- transforms.CenterCrop(256),
- transforms.ToTensor(),
- transforms.Normalize([0.485, 0.456, 0.406],
- [0.229, 0.224, 0.225])])}
- train_data = torchvision.datasets.CIFAR10ImageFolder(train_dir, transform=data_transforms['train_transform'])
- valid_data = torchvision.datasets.ImageFolder(valid_dir, transform=data_transforms['valid_transform'])
- test_data = torchvision.datasets.ImageFolder(test_dir, transform=data_transforms['test_transform'])
- image_datasets={
- 'train_data':torchvision.datasets.ImageFolder(train_dir, train_data),
- 'valid_data':torchvision.datasets.ImageFolder(valid_dir, valid_data),
- 'test_data': torchvision.datasets.ImageFolder(train_dir, test_data)}
- train_loader = torch.utils.data.DataLoader(image_datasets['train_data'], batch_size=20,shuffle=True)
- valid_loader = torch.utils.data.DataLoader(image_datasets['valid_data'], batch_size=20,shuffle=True)
- test_loader = torch.utils.data.DataLoader(image_datasets['test_data'], batch_size=20,shuffle=True)
- loaders_scratch={
- 'train':train_loader,
- 'valid': train_loader,
- 'test': test_loader}
- import torch.nn as nn
- import torch.nn.functional as F
- # define the CNN architecture
- class Net(nn.Module):
- ### TODO: choose an architecture, and complete the class
- def __init__(self):
- super(Net, self).__init__()
- ## Define layers of a CNN
- self.conv1 = nn.Conv2d(3, 32, 3, padding=1)
- self.conv2 = nn.Conv2d(32, 64, 3, padding=1)
- self.conv3 = nn.Conv2d(64, 128, 3, padding=1)
- # max pooling layer
- self.max_pool = nn.MaxPool2d(2, 2)
- self.relu = nn.ReLU(inplace=True)
- self.fc1 = nn.Linear(7 * 7 * 128, 500)
- self.fc2 = nn.Linear(500, 133)
- self.dropout = nn.Dropout(0.25)
- def forward(self, x):
- ## Define forward behavior
- x = F.relu(self.conv1(x))
- x = self.max_pool(x)
- x = F.relu(self.conv2(x))
- x = self.max_pool(x)
- x = F.relu(self.conv3(x))
- x = self.max_pool(x)
- # flatten image input
- x = x.view(-1, 7 * 7 * 128)
- # add dropout layer
- x = self.dropout(x)
- x = F.relu(self.fc1(x))
- # add dropout layer
- x = self.dropout(x)
- x = self.fc2(x)
- return x
- #-#-# You so NOT have to modify the code below this line. #-#-#
- # instantiate the CNN
- model_scratch = Net()
- # move tensors to GPU if CUDA is available
- if use_cuda:
- model_scratch.cuda()
- import torch.optim as optim
- ### TODO: select loss function
- criterion_scratch = nn.CrossEntropyLoss()
- ### TODO: select optimizer
- optimizer_scratch = optim.SGD(model_scratch.parameters(), lr = 0.05)
- def train(n_epochs, loaders, model, optimizer, criterion, use_cuda, save_path):
- """returns trained model"""
- # initialize tracker for minimum validation loss
- valid_loss_min = np.Inf
- for epoch in range(1, n_epochs+1):
- # initialize variables to monitor training and validation loss
- train_loss = 0.0
- valid_loss = 0.0
- ###################
- # train the model #
- ###################
- model.train()
- for batch_idx, (data, target) in enumerate(loaders['train']):
- # move to GPU
- if use_cuda:
- data, target = data.cuda(), target.cuda()
- ## find the loss and update the model parameters accordingly
- ## record the average training loss, using something like
- ## train_loss = train_loss + ((1 / (batch_idx + 1)) * (loss.data - train_loss))
- optimizer.zero_grad()
- # forward pass
- output = model(data)
- # calculate the loss
- loss = criterion(output, target)
- # backward pass
- loss.backward()
- # perform optimization step
- optimizer.step()
- # update training loss
- train_loss += ((1 / (batch_idx + 1)) * (loss.data - train_loss))
- #train_loss += loss.item()*data.size(0)
- ######################
- # validate the model #
- ######################
- model.eval()
- for batch_idx, (data, target) in enumerate(loaders['valid']):
- # move to GPU
- if use_cuda:
- data, target = data.cuda(), target.cuda()
- ## update the average validation loss
- output = model(data)
- loss = criterion(output, target)
- valid_loss += ((1 / (batch_idx + 1)) * (loss.data - valid_loss))
- # print training/validation statistics
- print('Epoch: {} \tTraining Loss: {:.6f} \tValidation Loss: {:.6f}'.format(
- epoch,
- train_loss,
- valid_loss
- ))
- ## TODO: save the model if validation loss has decreased
- if valid_loss <= valid_loss_min:
- valid_loss_min = valid_loss
- print('Validation loss decreased ({:.6f} --> {:.6f}). Saving model ...'.format(
- valid_loss_min,
- valid_loss))
- torch.save(model.state_dict(), save_path)
- # return trained model
- return model
- # train the model
- model_scratch = train(20, loaders_scratch, model_scratch, optimizer_scratch,criterion_scratch, use_cuda, 'model_scratch.pt')
- # load the model that got the best validation accuracy
- model_scratch.load_state_dict(torch.load('model_scratch.pt'))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement