인공신경망
참고링크: https://wikidocs.net/60680
활성화 함수
활성화 함수(activation function)이란 입력 신호의 총합을 출력 신호로 변환하는 함수를 의미한다. 인공 신경망의 활성화 함수는 비선형 함수를 사용해야 한다.
-
시그모이드(sigmoid)
-
ReLU (Rectified Linear Unit)
단층 퍼셉트론
nn.Linear
는 PyTorch에서 사용되는 선형 변환(linear transformation)을 수행하는 클래스이다. 두 개의 행렬 가중치(weight)와 편향(bias)을 학습하며, 입력 텐서를 선형 변환하여 출력 텐서를 생성한다. 선형 변환은 입력 텐서와 가중치 행렬의 행렬 곱을 계산하고, 편향을 더하는 연산으로 이루어진다.
torch.ones()
로 입력값 weight을 모두 1로 초기화nn.Linear
로 linear layer 생성nn.ReLU()
로 활성화 함수 생성- 입력값을 linear layer에 넣어서 output 생성
- output을 ReLU에 넣어서 결과 출력
import torch
import torch.nn as nn
input_size = 10
output_size = 5
input_data = torch.ones(input_size) # input_size 크기의 1로 채워진 텐서 생성
linear_layer = nn.Linear(input_size, output_size)
relu = nn.ReLU()
output = linear_layer(input_data)
output_relu = relu(output)
print(output_relu)
nn.Linear
클래스를 사용하지 않고 수동으로 해줄 수도 있다. 이때 @
연산자는 행렬곱을 의미한다.
output_manual = input_data @ linear_layer.weight.data.T + linear_layer.bias.data
print("Manual linear output:", output_manual)
다층 퍼셉트론 (MLP)
은닉층인 hidden_layer
부분이 다르다. nn.Sequential
을 사용하여 입력층, 은닉층, 출력층을 모은다.
input_size = 4
hidden_size = 5
output_size = 3
input_data = torch.ones(input_size)
linear_layer = nn.Linear(input_size, hidden_size)
hidden_layer = nn.Linear(hidden_size, output_size)
relu = nn.ReLU()
model = nn.Sequential(linear_layer, relu, hidden_layer)
output = model(input_data)
print(output)
nn.Sequential
에서 linear_layer
, relu
, hidden_layer
순으로 쌓는 이유가 무엇인가? 참고
즉 은닉층을 와 를 사용해서 로 재구성할 수 있기 때문에, 다층이 아닌 단층 퍼셉트론이 된다. 이를 해결하는 방법은 모든 층의 다음에 와 같은 비선형 함수 를 추가하는 것이다. 즉,
역전파
역전파(backpropagation)란, 계산 결과와 정답의 오차를 구해 이 오차에 관여하는 값들의 가증치를 수정하여 오차가 작아지는 방향으로 반복 수정하는 방법이다.
손실함수 MSE와 Adam optimizer를 사용하여 진행해보자.
평균제곱오차(Mean Squared Error, MSE)는 오차를 제곱한 값의 평균 이다.
from torch.optim import Adam
loss_fn = nn.MSELoss()
ground_truth = torch.tensor([0, 0.5, 1], dtype=torch.float)
optimizer = Adam(model.parameters(), lr=0.1)
while True: # backpropagate until the loss is small enough
optimizer.zero_grad() # 1. Clear gradient
output = model(input_data) # 2. Forward propagation
loss = loss_fn(output, ground_truth) # 3. Compute loss
loss.backward() # 4. Backward propagation
optimizer.step() # 5. Update parameters
print(f"{i} Loss:", loss.item())
if loss.item() < 1e-5:
break
i += 1
print("Output:", model(input_data))
ground_truth
는 우리가 인공지능에게 입력해주는 desired output이다. 즉,[0, 0.5, 1]
과 미만의 오차를 갖는 값이 나올 떄까지 반복하라는 의미다.
Adam
으로 optimizer를 생성할 때lr
라는 파라미터가 있는데 이는 학습률을 의미한다. 다음을 참고하기 바란다.