개요
인공 신경망을 최적화하는 과정에서 미분은 필수적인 요소이다. PyTorch는 이러한 최적화 과정인 역전파(backpropagation) 를 손쉽게 수행할 수 있도록 자동 미분(Automatic Differentiation) 기능을 제공한다. 이번 포스팅에서는 PyTorch에서 역전파를 사용하는 방법과 자동 미분의 기본 개념을 단계별로 살펴본다.
역전파란?
역전파는 신경망의 가중치를 최적화하기 위해 손실 함수의 기울기를 계산하는 알고리즘이다. 이 과정에서 체인 룰(연쇄 법칙)을 사용하여 각 가중치에 대한 손실 함수의 미분값을 효율적으로 계산한다. PyTorch는 자동 미분 기능을 통해 이러한 계산을 자동으로 처리해준다.
자동 미분 준비하기
자동 미분을 사용하기 위해서는 먼저 필요한 라이브러리를 불러오고, 미분을 추적할 텐서를 설정해야 한다.
라이브러리 불러오기
먼저 PyTorch 라이브러리를 불러온다.
import torch
텐서 생성 및 미분 추적 설정
requires_grad=True 옵션을 사용하여 텐서가 연산 그래프에서 미분을 추적하도록 설정할 수 있다. 이를 통해 텐서에 대한 모든 연산이 기록되고, 역전파 시 자동으로 기울기가 계산된다.
# requires_grad=True는 해당 텐서를 기준으로 모든 연산들을 추적할 수 있게 하는 옵션이다.
# 즉, x에 대해서 연쇄 법칙을 이용한 미분이 가능하다는 것이다.
x = torch.ones(2, 2, requires_grad=True)
print(x)
# 출력 tensor([[1., 1.],
[1., 1.]], requires_grad=True)
연산 그래프 구성
이제 x 텐서를 기반으로 여러 연산을 수행하여 연산 그래프를 구성해보자.
# y는 x에 대한 식
y = x + 1
print("y: ", y)
# z는 y에 대한 식
z = 2 * y ** 2
print("z: ", z)
# res는 z에 대한 식 (손실 함수로 가정)
res = z.mean()
print("Result: ", res)
# 출력
# y: tensor([[2., 2.],
# [2., 2.]], grad_fn=<AddBackward0>)
# z: tensor([[ 8., 8.],
# [ 8., 8.]], grad_fn=<MulBackward0>)
# Result: tensor(8., grad_fn=<MeanBackward0>)
위 출력에서 grad_fn=<...>은 해당 텐서가 연산 그래프에서 생성된 것임을 의미한다. 이는 PyTorch가 자동으로 연산을 추적하고 있음을 나타낸다.
역전파 수행하기
연산 그래프가 구성되었으므로, 이제 역전파를 통해 기울기를 계산할 수 있다. 이를 위해 backward() 메서드를 호출한다.
역전파 실행
# res를 기준으로 역전파를 수행
res.backward()
기울기 확인하기
역전파가 완료되면, x.grad 속성을 통해 x 텐서에 대한 기울기를 확인할 수 있다.
print(x)
print(x.grad)
기울기 계산 과정
위 예제에서 res는 다음과 같은 수식으로 표현된다
res = (1/4) * Σ(z_i) for i from 1 to 4 = (1/4) * Σ[2(x_i + 1)^2] for i from 1 to 4
따라서, 각 x_i에 대한 res의 기울기는 다음과 같이 계산된다
dx_i / d(res) = 2 * 2(x_i + 1) * (1/4) = (x_i + 1)
실제로 x.grad 값은 모든 x_i에 대해 2로 계산되었는데, 이는 x_i = 1이기 때문이다.
역전파의 중요성
역전파는 신경망의 학습 과정에서 손실 함수를 최소화하기 위해 가중치를 조정하는 데 필수적이다. 자동 미분을 사용하면 복잡한 미분 계산을 직접 수행하지 않고도 기울기를 쉽게 얻을 수 있어, 모델의 학습을 효율적으로 진행할 수 있다.
자동 미분의 주의사항
필요한 경우에만 미분 추적을 사용 해야한다.
불필요한 미분 추적은 메모리 사용량과 계산 시간을 증가시킬 수 있다. 학습이 필요 없는 경우 with torch.no_grad(): 블록을 사용하여 미분 추적을 비활성화할 수 있다.
with torch.no_grad():
y = x + 2
기울기를 초기화 해야한다.
반복 학습 과정에서 이전 기울기가 누적되지 않도록 optimizer.zero_grad() 또는 x.grad.zero_()를 사용하여 기울기를 초기화해야 한다.
x.grad.zero_()
in-place 연산을 주의 해야한다.
인-플레이스 연산은 연산 그래프를 변경시킬 수 있으므로, 자동 미분 과정에서 오류를 유발할 수 있다. 인-플레이스 연산을 사용할 때는 신중하게 사용해야 한다.
참고
[파이토치] 실전 인공지능으로 이어지는 딥러닝 - 기초부터 논문 구현까지 강의 | 딥러닝호형 -
딥러닝호형 | 인공지능 분야에서 활용도가 매우 높은 딥러닝 프레임워크인 Pytorch를 이용하여 다양한 인공 신경망을 구현하는 강의입니다., 왜 딥러닝 호형인가?📝 현재 딥러닝/머신러닝 관련
www.inflearn.com
'AI > 개념' 카테고리의 다른 글
PyTorch 데이터 불러오기 (0) | 2025.02.15 |
---|---|
혼동행렬(confusion matrix)이란 무엇인가? (0) | 2025.02.05 |
PyTorch 텐서(Tensor) 사용법 (0) | 2025.01.25 |
최적화 (Optimization)와 목적 함수(Objective Function)과 하강법 (Descent Method) (1) | 2024.10.14 |
손실 함수와 회귀(Regression) (0) | 2024.10.07 |