深度学习模型的构建一、DataLoader


前言

CV方向的深度学习算法的结构都大概差不多,大概由6部分构成:DataLoader,Loss、optimizer、lr_scheduler、module、结果可视化。接下来我会一一进行总结。

一、DataLoader

Dataloader的作用是加载数据集,为网络的训练提供数据。构建时首先复写Dataset类, Dataset类里的__getitem__ 函数被用来获取单个的数据,然后传入到DataLoader中组合成batch,再使用collate_fn所指定的函数对这个batch做一些操作,比如padding啊之类的。

  • 因为不同的数据保存的格式都不一样,还要经过不同的处理变换,所以我们会经常去复写Dataset类。
  • 我复写时的习惯是在__init__中构建所有样本和标签的索引列表self.data,在__getitem__里对样本和标签进行变换。
class MyDatasets(Dataset):

    """
    通过包含数据路径和要指定为分类的类名
    data_path:数据路径,到train或者val
    img_true:二分类中,指定的类
    transform: 数据处理,对图像进行随机裁剪, 以及转换成tensor。外界定义好是train的tranform或者是val的transform,然后传进来。也可以在里面定义
    """

    def __init__(self, data_path, img_true, transform=None):
        super(ImageDataset,self).__init__()
        data_floder = os.listdir(data_path)
        data = []
        for item in data_floder:
            img_list = os.listdir(os.path.join(data_path,item))
            
            for img in img_list:
                if item == img_true:
                    data.append((os.path.join(data_path,item,img),int(1)))
                else:
                    data.append((os.path.join(data_path,item,img),int(0)))
                
        self.data = data
        self.transform = transform # 对输入图像进行预处理,这里并没有做,预设为None

      
    def __getitem__(self,idx):
        image_name, labels = self.data[idx]
        image = Image.open(image_name)
        if self.transform:
            data = self.transform(image)
        return data,labels
                 
    def __len__(self):
        return len(self.data)

Dataset类构建好之后,就可以传入到DataLoader中组合成batch,继续上代码。

torch.utils.data.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
参数:
  • dataset(Dataset): 传入的数据集
  • batch_size(int, optional): 每个batch有多少个样本
  • shuffle(bool, optional): 在每个epoch开始的时候,对数据进行重新排序
  • sampler(Sampler, optional): 自定义从数据集中取样本的策略,如果指定这个参数,那么shuffle必须为False
  • batch_sampler(Sampler, optional): 与sampler类似,但是一次只返回一个batch的indices(索引),需要注意的是,一旦指定了这个参数,那么batch_size,shuffle,sampler,drop_last就不能再制定了(互斥——Mutually exclusive)
  • num_workers (int, optional): 这个参数决定了有几个进程来处理data loading。0意味着所有的数据都会被load进主进程。(默认为0)
  • collate_fn (callable, optional): 将一个list的sample组成一个mini-batch的函数
  • pin_memory (bool, optional): 如果设置为True,那么data loader将会在返回它们之前,将tensors拷贝到CUDA中的固定内存(CUDA pinned memory)中.
  • drop_last (bool, optional): 如果设置为True:这个是对最后的未完成的batch来说的,比如你的batch_size设置为64,而一个epoch只有100个样本,那么训练的时候后面的36个就被扔掉了…
    如果为False(默认),那么会继续正常执行,只是最后的batch_size会小一点。
  • timeout(numeric, optional): 如果是正数,表明等待从worker进程中收集一个batch等待的时间,若超出设定的时间还没有收集到,那就不收集这个内容了。这个numeric应总是大于等于0。默认为0
  • worker_init_fn (callable, optional): 每个worker初始化函数,是事先定义好的,可以用来分配每个worker的任务(num_workers >0时才需要他),如果num_workers >0(开启多进程)却没有手动配置每个进程的工作空间的话,默认每个进程的工作空间是整个dataset,因此每个进程都会遍历一次整个数据集,导致产生重复数据。
    直接用代码来举个例子:
	def worker_init_fn(worker_id):
	    worker_info = torch.utils.data.get_worker_info()
	    dataset = worker_info.dataset  # the dataset copy in this worker process
	    overall_start = dataset.start
	    overall_end = dataset.end
	    # configure the dataset to only process the split workload
	    per_worker = int(math.ceil((overall_end - overall_start) / float(worker_info.num_workers)))
	    worker_id = worker_info.id
	    dataset.start = overall_start + worker_id * per_worker
	    dataset.end = min(dataset.start + per_worker, overall_end)
  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值