# MindSpore报错ValueError: when loss\_fn is not None, train\_dataset should return two elements, but got 3

**1. 系统环境**

硬件环境\(Ascend/GPU/CPU\): Ascend/GPU/CPU

软件环境: MindSpore 版本: 1.1.0

执行模式： 不限

Python 版本: 3.7.5

操作系统平台: linux

**2. 报错信息**

2.1 问题描述

自定义数据集在第一轮可正常遍历，但第二轮时出现list index out of range。

2.2 报错信息

```
ValueError: when loss_fn is not None, train_dataset should return two elements, but got 3
```

2.3 脚本信息

```
import mindspore.dataset as ds
import matplotlib.pyplot as plt
import mindspore.dataset.vision.py_transforms as py_trans
from mindspore.dataset.transforms.py_transforms import Compose
import mindspore.ops as ops
# from mindspore import Tensor
import numpy as np
from PIL import Image
import os
import random
from option import opt

class DatasetGenerator:
    def __init__(self, path, train, format='.png'):
        # self.size = size
        self.format = format
        self.train = train
        if train:
            self.haze_imgs_dir = os.listdir(os.path.join(path, 'train', 'hazy'))
            self.haze_imgs = [os.path.join(path, 'train', 'hazy', img) for img in self.haze_imgs_dir]
            self.clear_dir = os.path.join(path, 'train', 'gt')
        else:
            self.haze_imgs_dir = os.listdir(os.path.join(path, 'test', 'hazy'))
            self.haze_imgs = [os.path.join(path, 'test', 'hazy', img) for img in self.haze_imgs_dir]
            self.clear_dir = os.path.join(path, 'test', 'gt')
        # print(self.haze_imgs_dir, self.clear_dir)
        np.random.seed(58)
        self.__random_seed = []
        for _ in range(len(self.haze_imgs)):
            self.__random_seed.append(random.randint(0, 1000000))
        self.__index = -1

    def __getitem__(self, index):
        self.__index += 1
        haze = Image.open(self.haze_imgs[index])
        # if isinstance(self.size,int):
        #     while haze.size[0]<self.size or haze.size[1]<self.size :
        #         index=random.randint(0,20000)
        #         haze=Image.open(self.haze_imgs[index])
        img = self.haze_imgs[index].split('\\')[-1]
        # img=self.haze_imgs[index].split('/')[-1]
        img_name = img.split('_')
        # img_name=img.split('\\')[-1].split('_')
        # print(img_name)
        clear_name=f"{img_name[0]}_gt_{img_name[2]}"
        # print(self.clear_dir, clear_name, os.path.join(self.clear_dir,clear_name))
        clear=Image.open(os.path.join(self.clear_dir,clear_name))
        w, h = clear.size
        nw, nh = haze.size
        left = (w - nw)/2
        top = (h - nh)/2
        right = (w + nw)/2
        bottom = (h + nh)/2
        clear = clear.crop((left, top, right, bottom))
        return (haze, clear, index)

    def __len__(self):
        print(len(self.haze_imgs))
        return len(self.haze_imgs)

    def get_seed(self):
        seed = self.__random_seed[self.__index]
        return seed

def decode(img):
    return Image.fromarray(img)

def set_random_seed(img_name, seed):
    random.seed(seed)
    return img_name

ds.config.set_seed(8)
# DATA_DIR = opt.data_url
DATA_DIR = 'C:\Users\kle\Desktop\NTIRE2021'

train_dataset_generator = DatasetGenerator(DATA_DIR, train=True)
train_dataset = ds.GeneratorDataset(train_dataset_generator, ["hazy", "gt", "img_name"], shuffle=True)
test_dataset_generator = DatasetGenerator(DATA_DIR, train=False)
test_dataset = ds.GeneratorDataset(test_dataset_generator, ["hazy", "gt", "img_name"], shuffle=False)
transforms_list = [
    decode,
    (lambda img_name: set_random_seed(img_name, train_dataset_generator.get_seed())),
    py_trans.RandomCrop(opt.crop_size),
    py_trans.ToTensor(),
]
compose_trans = Compose(transforms_list)
train_dataset = train_dataset.map(operations=compose_trans, input_columns=["hazy"])
train_dataset = train_dataset.map(operations=compose_trans, input_columns=["gt"])
train_dataset = train_dataset.batch(opt.bs, drop_remainder=True)

if __name__ == '__main__':
    for i in range(2):
        print(i)
        for batch in train_dataset.create_dict_iterator():
            # print(batch)
            # hazy = Tensor(batch["hazy"], dtype=mindspore.float32)
            # clear = Tensor(batch["gt"], dtype=mindspore.float32)
            print(batch["hazy"].shape, batch["gt"].shape)
```

**3. 根因分析**

脚本中第37行利用魔术方法 def \_\_getitem\_\_\(self, index\)定义了随机访问的类，其中index参数作为样本\\元素索引，外部可以直接使用index来进行数据的访问，外部不需要对其进行修改（如：每个迭代开始前的复位操作）。

但是在代码的第35行户另外自定义了\_\_index，所以需要在每个迭代前进行复位操作，来保证不出现数组越界访问。

**4. 解决方案**

根据根因分析提供的信息，已经非常清楚，就是在另外每次迭代再重新使用\_\_index时，每次迭代完后都进行了

```
self.__index = -1
```

造成了下次迭代没有复位的问题，那么可以很简单的让它等于初始值即可。

```
self.__index += 0
```

