如何在 Pytorch 中测试自定义数据集?

Posted

技术标签:

【中文标题】如何在 Pytorch 中测试自定义数据集?【英文标题】:How do you test a custom dataset in Pytorch? 【发布时间】:2021-07-21 07:09:54 【问题描述】:

我一直在关注 Pytorch 中使用来自 Pytorch 的数据集的教程,这些教程允许您启用是否要使用数据进行训练...但现在我使用的是 .csv 和自定义数据集。

class MyDataset(Dataset):
    def __init__(self, root, n_inp):
        self.df = pd.read_csv(root)
        self.data = self.df.to_numpy()
        self.x , self.y = (torch.from_numpy(self.data[:,:n_inp]),
                           torch.from_numpy(self.data[:,n_inp:]))
    def __getitem__(self, idx):
        return self.x[idx, :], self.y[idx,:]
    def __len__(self):
        return len(self.data)

我如何告诉 Pytorch 不要训练我的 test_dataset,以便我可以将其用作我的模型准确度的参考?

train_dataset = MyDataset("heart.csv", input_size)
train_loader = DataLoader(train_dataset, batch_size=batch_size, shuffle =True)
test_dataset = MyDataset("heart.csv", input_size)
test_loader = DataLoader(test_dataset, batch_size=batch_size, shuffle =True)

【问题讨论】:

【参考方案1】:

在 pytorch 中,自定义数据集继承类 Dataset。主要包含两个方法__len__()是指定要迭代的数据集对象的长度,__getitem__()是一次返回一批数据。

一旦数据加载器对象被初始化(train_loadertest_loader 在您的代码中指定),您需要编写一个训练循环和一个测试循环。

def train(model, optimizer, loss_fn, dataloader):
    model.train()
    for i, (input, gt) in enumerate(dataloader):
        if params.use_gpu: #(If training using GPU)
            input, gt = input.cuda(non_blocking = True), gt.cuda(non_blocking = True)
        predicted = model(input)
        loss = loss_fn(predicted, gt)
        optimizer.zero_grad()
        loss.backward()
        optimizer.step()

你的测试循环应该是:

def test(model,loss_fn, dataloader):
    model.eval()
    for i, (input, gt) in enumerate(dataloader):
        if params.use_gpu: #(If training using GPU)
            input, gt = input.cuda(non_blocking = True), gt.cuda(non_blocking = True)
        predicted = model(input)
        loss     = loss_fn(predicted, gt)

此外,您可以使用指标字典来记录您的预测、损失、时期等。训练循环和测试循环的主要区别在于我们在推理阶段排除了反向传播(zero_grad(), backward(), step())。

最后,

for epoch in range(1, epochs + 1):
    train(model, optimizer, loss_fn, train_loader)
    test(model, loss_fn, test_loader)

【讨论】:

【参考方案2】:

在 pytorch 中进行测试时需要注意以下几点:

    将您的模型置于评估模式,这样dropout 和batch normalization 之类的东西就不会进入训练模式:model.eval() 在您的测试代码周围放置一个包装器以避免计算梯度(节省内存和时间):with torch.no_grad(): 仅根据您的训练集规范化或标准化您的数据。这对于最小/最大归一化或 z 分数标准化很重要,以便模型准确反映测试性能。

除此之外,您编写的内容在我看来还不错,因为您没有对数据应用任何转换(例如,图像翻转或高斯噪声注入)。要显示测试模式下的代码应该是什么样子,请参见下文:

for e in range(num_epochs):
    for B, (dat, label) in enumerate(train_loader):
         #transforms here
         opt.zero_grad()
         out = model(dat.to(device))
         loss = criterion(out)
         loss.backward()
         opt.step()
    with torch.no_grad():
         model.eval()
         global_corr = 0
         for B, (dat,label) in enumerate(test_loader):
             out = model(dat.to(device))
             # get batch eval metrics here!

     

【讨论】:

以上是关于如何在 Pytorch 中测试自定义数据集?的主要内容,如果未能解决你的问题,请参考以下文章

Pytorch 自定义Function

如何将基于自定义图像的数据集加载到 Pytorch 中以与 CNN 一起使用?

Pytorch自定义数据集模型训练流程

在PyTorch中构建高效的自定义数据集

PyTorch自定义数据集处理/dataset/DataLoader等

PyTorch自定义数据集处理/dataset/DataLoader等