(6주차) 10월14일
미니배치
-
(1/4) 시험일정 공지
-
(2/4) 미니배치
-
(3/4) 딥러닝용 컴퓨터를 고르는 요령
-
(4/4) 과제설명
import torch
from fastai.vision.all import *
X=torch.tensor([3.0, 4.0, 5.0, 6.0, 7.0, 8.0, 9.0])
y=torch.tensor([1.0, 0.0, 1.0, 0.0, 1.0, 1.0, 0.0])
X,y
ds=torch.utils.data.TensorDataset(X,y)
ds ## 그냥 텐서들의 pair
ds.tensors
-
배치사이즈=2, 셔플= True,
dl=torch.utils.data.DataLoader(ds,batch_size=2,shuffle=True)
dl
dir(dl)
- dl은 배치를 만드는 기능이 있어보임
for xx,yy in dl:
print(xx,yy)
-
배치사이즈=2, 셔플= False
dl=torch.utils.data.DataLoader(ds,batch_size=2,shuffle=False)
for xx,yy in dl:
print(xx,yy)
-
배치사이즈=3, 셔플= True
dl=torch.utils.data.DataLoader(ds,batch_size=3,shuffle=True)
for xx,yy in dl:
print(xx,yy)
-
우선 텐서로 이루어진 X,y를 만들자.
path = untar_data(URLs.MNIST_SAMPLE)
threes=(path/'train'/'3').ls()
sevens=(path/'train'/'7').ls()
seven_tensor = torch.stack([tensor(Image.open(i)) for i in sevens]).float()/255
three_tensor = torch.stack([tensor(Image.open(i)) for i in threes]).float()/255
X=torch.vstack([seven_tensor,three_tensor]).reshape(12396,-1)
y=torch.tensor([0.0]*6265 + [1.0]*6131).reshape(12396,1)
-
dataset=(X,y) 를 만들자.
ds=torch.utils.data.TensorDataset(X,y)
-
dataloader를 만들자.
dl=torch.utils.data.DataLoader(ds,batch_size=2048,shuffle=True)
-
네트워크(아키텍처), 손실함수, 옵티마이저
torch.manual_seed(1)
net = torch.nn.Sequential(
torch.nn.Linear(in_features=784,out_features=30),
torch.nn.ReLU(),
torch.nn.Linear(in_features=30,out_features=1)
#torch.nn.Sigmoid()
)
loss_fn=torch.nn.BCEWithLogitsLoss()
optimizer=torch.optim.Adam(net.parameters())
-
저번시간 복습
for epoc in range(200):
## 1
yhat=net(X)
## 2
loss= loss_fn(yhat,y)
## 3
loss.backward()
## 4
optimizer.step()
net.zero_grad()
plt.plot(yhat.data,'.')
f=torch.nn.Sigmoid()
plt.plot(f(yhat.data),'.')
-
미니배치활용
torch.manual_seed(1)
net = torch.nn.Sequential(
torch.nn.Linear(in_features=784,out_features=30),
torch.nn.ReLU(),
torch.nn.Linear(in_features=30,out_features=1)
#torch.nn.Sigmoid()
)
loss_fn=torch.nn.BCEWithLogitsLoss()
optimizer=torch.optim.Adam(net.parameters())
- 네트워크 파라메터 다시 초기화
12396 / 2048
- 총 7개의 미니배치가 만들어질것임 $\to$ 따라서 파라메터를 업데이트하는 횟수는 7 $\times$ epoc 임 (실제적으로는 6 $\times$ epoc)
200/6
for epoc in range(33):
for xx,yy in dl: ### 총 7번돌면 끝나는 for
## 1
yyhat=net(xx)
## 2
loss= loss_fn(yyhat,yy)
## 3
loss.backward()
## 4
optimizer.step()
net.zero_grad()
plt.plot(yyhat.data,'.')
- 이게 왜이러지??
-
배치사이즈를 다시 확인해보자.
for xx,yy in dl:
print(xx.shape,yy.shape)
-
마지막이 108개이므로 108개의 y만 그려짐
plt.plot(net(X).data,'.')
-
2048개 정도만 대충학습해도 동일 반복횟수에 대하여 거의 대등한 효율이 나옴
-
GPU에 있는 메모리로 12396개의 데이터를 모두 보내지 않아도 괜찮겠다 $\to$ 그래픽카드의 메모리를 얼마나 큰 것으로 살지는 자료의 크기와는 상관없다.
-
net.parameters()에 저장된 값들은 그대로 GPU로 가야만한다. $\to$ 그래픽카드의 메모리를 얼마나 큰것으로 살지는 모형의 복잡도와 관련이 있다.
컴퓨터사는방법
- 메모리: $n$이 큰 자료를 다룰수록 메모리가 커야한다.
- GPU의 메모리: 모형의 복잡도가 커질수록 GPU의 메모리가 커야한다.