1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114
| import matplotlib.pyplot as plt import torch import torch.nn as nn import torchvision from torch.utils.data import DataLoader
batch_size = 64 train_loss = []
train_dataloader = DataLoader( torchvision.datasets.MNIST( './data/', train=True, download=False, transform=torchvision.transforms.Compose([ torchvision.transforms.ToTensor(), torchvision.transforms.Normalize( (0.1307,), (0.3081,) ) ]) ), batch_size=batch_size, shuffle=True ) test_dataloader = DataLoader( torchvision.datasets.MNIST( './data/', train=False, download=False, transform=torchvision.transforms.Compose([ torchvision.transforms.ToTensor(), torchvision.transforms.Normalize( (0.1307,), (0.3081,) ) ]) ), batch_size=batch_size, shuffle=True )
device = "cuda" if torch.cuda.is_available() else "cpu"
class NeuralNetwork(nn.Module): def __init__(self): super().__init__() self.flatten = nn.Flatten() self.linear_relu_stack = nn.Sequential( nn.Linear(28*28, 512), nn.ReLU(), nn.Linear(512, 512), nn.ReLU(), nn.Linear(512, 10) ) def forward(self, x): x = self.flatten(x) return self.linear_relu_stack(x)
model = NeuralNetwork().to(device) print(model)
def train(dataloader, model, loss_fn, optimizer): size = len(dataloader.dataset) model.train() for batch, (X, y) in enumerate(dataloader): X, y = X.to(device), y.to(device) ''' here model is called, see module.py(line 1124) for more detail about implementation of call ''' pred = model(X) loss = loss_fn(pred, y)
optimizer.zero_grad() loss.backward() optimizer.step()
if batch % 100 == 0: loss, current = loss.item(), batch * len(X) train_loss.append(loss) print(f"loss: {loss:>7f} [{current:>5d}/{size:>5d}]")
def test(dataloader, model, loss_fn): size = len(dataloader.dataset) num_batches = len(dataloader) model.eval() test_loss, correct = 0, 0 with torch.no_grad(): for X, y in dataloader: X, y = X.to(device), y.to(device) pred = model(X) test_loss += loss_fn(pred, y).item() correct += (pred.argmax(1) == y).type(torch.float).sum().item() test_loss /= num_batches correct /= size print(f"Test Error: \n Accuracy: {(100*correct):>0.1f}%, Avg loss: {test_loss:>8f} \n")
loss_fn = nn.CrossEntropyLoss() optimizer = torch.optim.SGD(model.parameters(), lr=1e-3)
epochs = 5 for t in range(epochs): print(f"Epoch {t+1}\n-------------------------------") train(train_dataloader, model, loss_fn, optimizer) test(test_dataloader, model, loss_fn)
plt.plot([100 * (i + 1) for i in range(len(train_loss))], train_loss, 'r') plt.title('Train Loss') plt.show()
|