defforward(self, X): A = X for i inrange(self.num_layer): Z = torch.matmul(self.W[i], A) + self.b[i] if i == self.num_layer - 1: A = F.softmax(Z, 0) else: A = F.relu(Z)
return A
defloss(self, Y, Y_hat): return self.loss_fn(Y_hat.T, Y)
deftrain(model: MulticlassClassificationNet, X, Y, step, learning_rate, print_interval=100): optimizer = torch.optim.Adam(model.trainable_vars, learning_rate) for s inrange(step): Y_hat = model.forward(X) cost = model.loss(Y, Y_hat) optimizer.zero_grad() cost.backward() optimizer.step()
对比上一节的训练代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14
for e inrange(total_epoch): for mini_batch_X, mini_batch_Y in mini_batch_XYs: mini_batch_Y_hat = model.forward(mini_batch_X) model.backward(mini_batch_Y) optimizer.zero_grad() optimizer.add_grad(model.get_grad_dict()) optimizer.step()
currrent_epoch = optimizer.epoch
if currrent_epoch % print_interval == 0: # print loss ... optimizer.increase_epoch()
defforward(self, X): A = X for i, layer inenumerate(self.layers): A = layer(A) if i == self.num_layer - 1: A = F.softmax(A, dim=1) else: A = F.relu(A) return A
defloss(self, Y, Y_hat): return self.loss_fn(Y_hat, Y)
defevaluate(self, X, Y, return_loss=False): Y_hat = self.forward(X) Y_hat_predict = torch.argmax(Y_hat, dim=1) accuracy = (Y == Y_hat_predict).float().mean() if return_loss: loss = self.loss(Y, Y_hat) return accuracy, loss else: return accuracy
deftrain(model: MulticlassClassificationNet, X, Y, step, learning_rate, print_interval=100): optimizer = torch.optim.Adam(model.parameters(), learning_rate) for s inrange(step): Y_hat = model(X) cost = model.loss(Y, Y_hat) optimizer.zero_grad() cost.backward() optimizer.step() if s % print_interval == 0: accuracy, loss = model.evaluate(X, Y, return_loss=True) print(f'Step: {s}') print(f'Accuracy: {accuracy.item()}') print(f'Train loss: {loss.item()}') #保存模型 torch.save(model.state_dict(), save_path)