###### tags: `pytorch入門` [參考連結 microsoft介紹](https://docs.microsoft.com/zh-tw/learn/modules/intro-machine-learning-pytorch/) [參考連結 Datasets vs Dataloaders](https://iter01.com/524561.html) # ch3 使用 PyTorch 資料集和 DataLoaders 載入資料 ## Datasets and Dataloaders > 因處理數據的程式碼太混亂和難維持,所以pytorch提供了2種data primitives > `torch.utils.data.DataLoader` and `torch.utils.data.Dataset` > 允許你使用pre-loaded的資料集和你的資料集 > `Dataset`存data和相對應的特徵(label) => 你定義一個class去代表資料集 > `DataLoader`則是將`Dataset`用一個可迭代的東西打包,讓你可以更方便的獲取samples ## 構建Dataset的子類: ### 簡單組 ```python= import torch from torch.utils.data import Dataset,DataLoader class MyDataset(Dataset): def __init__(self): self.data = torch.tensor([[1,2,3],[2,3,4],[3,4,5],[4,5,6]]) self.label = torch.LongTensor([1,1,0,0]) def __getitem__(self,index): return self.data[index],self.label[index] def __len__(self): return len(self.data) ``` #### (1) __init__: > 一般是把資料直接儲存在這個類的屬性中。像是`self.data`,`self.label` #### (2) __getitem__: > index是一個索引,這個索引的的取值範圍根據__len__的值決定。 > 如果是測試集,就只返回資料 #### (3) __len__: > 資料長度 ### 讀取資料夾中檔案組 ```python= import os import pandas as pd import torchvision.io as tvio class CustomImageDataset(Dataset): def __init__(self, annotations_file, img_dir, transform=None, target_transform=None): self.img_labels = pd.read_csv(annotations_file) self.img_dir = img_dir self.transform = transform self.target_transform = target_transform def __len__(self): return len(self.img_labels) def __getitem__(self, idx): img_path = os.path.join(self.img_dir, self.img_labels.iloc[idx, 0]) #將圖像路徑進行拼接 image = tvio.read_image(img_path) #讀取圖片 label = self.img_labels.iloc[idx, 1] #讀取csv #這裡這樣寫應該是第0列=檔名,第1列=label if self.transform: image = self.transform(image) #還在研究 if self.target_transform: label = self.target_transform(label) #還在研究 sample = {"image": image, "label": label} #將資料和特徵轉換成字典格式 return sample ``` #### (1) __init__: > `annotations_file` 代表存label的csv路徑 > `img_dir` 如其名,圖像的路徑 #### (2) __len__: > return 長度(這裡是以label長度,要用data也可以) #### (3) __getitem__: > 根據輸入的索引idx,回傳一個字典格式(資料(img)+特徵(種類)) > 如果是測試集,就只返回資料 ## Preparing your data for training with DataLoaders ```python= mydataloader = DataLoader(dataset=mydataset, batch_size=1) ``` > batch_size 一次用幾個樣本作整個神經網路的導數運算來更新導數。 > 這個時候執行結果會依照資料的順序執行 ```python= mydataloader = DataLoader(dataset=mydataset, batch_size=2, shuffle=True) ``` > 而在我們增加了`shuffle=True`後,他則會打亂資料順序去執行。 ## 總結及補充 > Dataloader和Dataset兩個類是非常方便的,因為這個可以快速的做出來batch資料,修改batch_size和亂序都非常地方便。有下面兩個希望注意的地方: > 1. 一般標籤值應該是Long整數的,所以標籤的tensor可以用`torch.LongTensor`(資料)或者用`.long()`來轉化成Long整數的形式。 > 2. 如果要使用PyTorch的GPU訓練的話,一般是先判斷cuda是否可用,然後把資料標籤都==用`.to()`放到GPU視訊記憶體上進行GPU加速==。 ```python= device = 'cuda' if torch.cuda.is_available() else 'cpu' for i,(data,label) in enumerate(mydataloader): data = data.to(device) label = label.to(device) print(data,label) ```