[Pytorch] Autograd and Optimizer

hyunsooo·2022년 9월 27일
0
  • 딥러닝이란 하나의 레고(layer)를 정의한 후 이 블럭을 쌓아 올리는 구조라고 이해할 수 있다.

  • 딥러닝을 구성하는 Layer의 base class는 torch.nn.Module이다.

  • input, output, forward, backward(autograd) 정의한다.

  • 학습이 대상이 되는 parameter(tensor)로 정의한다.


nn.Parameter

  • Tensor 객체의 상속 객체

  • nn.Module 내에 attribute가 될 때는 requred_grad = True로 지정되어 학습 대상이 되는 Tensor가 된다.

  • 우리가 직접 지정할 일은 없지만 기본적인 구성은 아래와 같다.

class MyLinear(nn.Module):
	def __init__(self, in_f, out_f):
    	super().__init__()
        self.in_f = in_f
        self.out_f = out_f
        
        self.weights = nn.Parameter(
        	torch.randn(in_f, out_f)
            )
        
        self.bias = nn.Parameter(
        	torch.randn(out_f)
            )
        
    def forward(self, x: Tensor):
    	return x @ self.weights + self.bias

AutoGrad

  • Backward시 Layer에 있는 Parameter들의 미분을 수행한다.

  • Forward의 결과값(예측치)과 실제값간의 차이(loss)에 대한 미분을 수행한다.

  • 해당값으로 Parameter를 업데이트한다.

optimizer.zero_grad()의 의미
이전의 기울기 값이 현재 영향을 주지 않기 위해 초기화 시키는 코드

  • 실제 backward는 Module단계에서 직접 지정가능하다. 하지만 AutoGrad기능으로 자동으로 해주기 때문에 해줄 필요가 없다.

  • Module에서 backward와 optimizer 오버라이딩이 가능하다.

  • 사용자가 직접 미분 수식을 써야하는 부담이 있지만 순서에 대해선 이해할 필요가 있다.

class LR(nn.Module):
    def __init__(self, dim, lr=torch.scalar_tensor(0.01)):
        super(LR, self).__init__()
        # intialize parameters
        self.w = torch.zeros(dim, 1, dtype=torch.float).to(device)
        self.b = torch.scalar_tensor(0).to(device)
        self.grads = {"dw": torch.zeros(dim, 1, dtype=torch.float).to(device),
                      "db": torch.scalar_tensor(0).to(device)}
        self.lr = lr.to(device)

    def forward(self, x):
        ## compute forward
        z = torch.mm(self.w.T, x) + self.b
        a = self.sigmoid(z)
        return a

    def sigmoid(self, z):
        return 1/(1 + torch.exp(-z))

    def backward(self, x, yhat, y):
        ## compute backward
        self.grads["dw"] = (1/x.shape[1]) * torch.mm(x, (yhat - y).T)
        self.grads["db"] = (1/x.shape[1]) * torch.sum(yhat - y)
    
    def optimize(self):
        ## optimization step
        self.w = self.w - self.lr * self.grads["dw"]
        self.b = self.b - self.lr * self.grads["db"]
  • 위의 코드는 pytorch를 쓰지 않고 직접 Logistic Regression을 구현한 것이다.

  • pytorch를 사용하면 위 처럼 밑단을 구현할 필요는 없지만 어떤식으로 동작하는지는 알아야 할 필요가 있다.

profile
지식 공유

0개의 댓글