[PyTorch] Dataset & DataLoader

지윤곽·2022년 3월 16일
1

Reference

Dataset & DataLoader 구조

Untitled

  1. 데이터 전처리 (preprocessing)
  2. dataset
    • init
    • len
    • getitem (map-style : 하나의 데이터를 불러올때 어떻게 출력할지 정의하는 부분)
  3. transforms : (이미지 데이터) ToTensor(), CenterCrop() 등의 처리를 해줌
  4. DataLoader : 모델에 feeding 할 batch 생성 (batch_size, shuffle)
  5. Model : 앞에서 처리한 데이터가 모델에 들어감

Dataset 클래스

  • 데이터의 입력 형태를 정의하는 클래스
  • Image, text, audio에 따라 다르게 정의해주어야 한다.
import torch
from torch.utils.data import Dataset

class CustomDataset(Dataset):
    def __init__(self, text, labels):
				# 초기 데이터 생성 방법 
        self.labels = labels
        self.data = text

    def __len__(self):
        return len(self.labels)

    def __getitem__(self, idx):
				# index 값을 주었을 때 반환되는 데이터 형태 (X,y)
        label = self.labels[idx]
        text = self.data[idx]
        sample = {'text' : text, 'class' : label}
        return sample
  • cpu와 gpu는 병렬적으로 처리가 가능하다. cpu는 tesnor로 변환해주고 gpu는 학습을 진행한다. (cpu가 tesnor로 변환하면 gpu에 넣고 바로 다시 data를 tensor를 변환하는 작업이 동시에 진행된다. 그래서 초반에 다 tensor로 변환하는게 아니라 학습 시점에 학습과 동시에 tensor로 바꿔줌) 따라서 image Tensor 변환은 학습이 필요한 시점에 병렬적으로 진행하기 때문에 init 부분에서 모두 정의할 필요가 없고 getitem에서 transform 함수를 통해 변형을 진행한다.
    • HuggingFace, fastai같은 라이브러리를 통해 간단하게 만들어 놓은 dataset 사용 가능

DataLoader 클래스

  • data의 batch 생성 : dataset은 한 인덱스의 데이터를 가져온다면 dataloader는 여러개의 데이터를 묶어서 가져오는 역할
  • 학습 직전에 데이터 변환 → GPU에 feed 하기 전 실행됨
  • Tensor 변환 + batch 처리
  1. 데이터 셋 생성
text = ['Happy', 'Amazing', 'Sad', 'Unhapy', 'Glum']
labels = ['Positive', 'Positive', 'Negative', 'Negative', 'Negative']
MyDataset = CustomDataset(text, labels)
  1. Dataloader generator
MyDataLoader = DataLoader(MyDataset, batch_size=3, shuffle=True)
for dataset in MyDataLoader:
    print(dataset)
#### 
{'Text': ['Amazing', 'Unhapy', 'Sad'], 'Class': ['Positive', 'Negative', 'Negative']}
{'Text': ['Happy', 'Glum'], 'Class': ['Positive', 'Negative']}

위의 결과값과 같이 batch size로 데이터 크기가 꼭 나눠지지 떨어지지 않아도 마지막에 남은 데이터가 출력된다.

☝ next(iter(MyDataLoader)) : MyDataLoader는 iterable한 객체이기 때문에 iter를 붙여주면 generator로 생성되고 next를 하면 다음 데이터를 추출 (원래 input된 상태로 있다가 호출하는 시점에 메모리에 올라가서 변환된 tensor로 출력됨)
  • ★ DataLaoder가 제너레이터로 구성된 이유: list 같은 경우 list 안에 속한 모든 데이터를 메모리에 올리기 때문에 list 크기만큼 메모리를 차지하게 된다. 하지만 generator의 경우 next() 메쏘드를 통해 차례로 값에 접근하기 때문에 사용할 때마다 메모리를 적재하게 된다. 결과적으로 규모가 큰 값을 다룰수록 generator의 효율성을 더욱 높아진다.

DataLoader(dataset, batch_size=1, shuffle=False, **sampler**=None, **batch_sampler**=None, num_workers=0, **collate_fn**=None, pin_memory=False, drop_last=False, timeout=0, worker_init_fn=None, *, prefetch_factor=2, persistent_workers=False)

  • sampler : 불균형한 데이터셋의 경우 클래스 비율에 맞게 데이터를 만들어주기 위해 사용.
  • collate_fn : 시계열 데이터에서 가변 길이의 input일때 제일 긴 데이터의 길이에 맞춰주는 padding을 하기 위해 사용됨(NLP). 이 외에도 DataLoader에서 출력되는 데이터의 형태가 원하는 형태가 아닐때 변형할 수 있는 커스텀 함수로 지정할 수 있다.

과제

  • 데이터 다운로드 부터 dataloader까지 구현해보기

torchvision.datasets에서 많은 데이터셋이 제공된다. 여기서 다운받아서 구현해봐라 →🎇 torchvision.datasets.MNIST 클론 코딩 !!!

profile
아는게 힘이다

0개의 댓글

관련 채용 정보