Python 如何在pytorch中洗牌批次?

Python 如何在pytorch中洗牌批次?,python,random,pytorch-dataloader,Python,Random,Pytorch Dataloader,如何在洗牌批次的同时保持每个批次中的序列不被缓冲 受所问问题的启发。[错误答案-使用上文] 创建数据集 dataset=[1,2,3,4,5,6,7,8,9]#实际使用torch.utils.data.dataset 创建一个非无序数据加载器 dataloader=dataloader(数据集,批量大小=64,随机播放=False) 将数据加载器强制转换为列表,并使用random的sample()函数 随机导入 dataloader=random.sample(列表(dataloader),

如何在洗牌批次的同时保持每个批次中的序列不被缓冲

受所问问题的启发。

[错误答案-使用上文]

  • 创建数据集
  • dataset=[1,2,3,4,5,6,7,8,9]#实际使用torch.utils.data.dataset
    
  • 创建一个非无序数据加载器
  • dataloader=dataloader(数据集,批量大小=64,随机播放=False)
    
  • 将数据加载器强制转换为
    列表
    ,并使用
    random
    sample()
    函数
  • 随机导入
    dataloader=random.sample(列表(dataloader),len(dataloader))
    

    也许有一种更好的方法可以使用定制的批量采样器或其他什么东西来实现这一点,但这对我来说太混乱了,所以上面的方法似乎很有效。

    虽然这并不是对你问题的直接回答。我想用你自己发布的答案来解决一个问题。在我看来,做以下事情是一个非常糟糕的主意:

    dataloader = random.sample(list(dataloader), len(dataloader))
    
    这首先破坏了创建数据集和数据加载器的全部目的。因为只要你调用
    list(dataloader)
    你就会把你的数据集编译成一个张量列表。换句话说,它将为数据集中的每个索引调用
    \uuuu getitem\uuu
    。数据加载器是一种按批(或更多,取决于工作人员的数量)加载数据的设计器,避免了一次将整个数据集加载到内存中

    这在处理需要从文件系统加载图像的图像时更为重要。这很关键,我相信你根本不应该这样做

    看看这里,使用一个虚拟数据集:

    class DS(Dataset):
        def __getitem__(self, _):
            return torch.rand(100)
    
        def __len__(self):
            return 10000
    
    dl = DataLoader(DS(), batch_size=16)
    x = list(dl)
    
    这里的
    x
    将包含10000个大小为100的张量,您的计算机可以处理这些张量。现在想象一下,拥有一个由10000个512x512 RGB图像组成的数据集,你无法在内存中保存那么多

    此外,我甚至没有提到数据增强。这仅在保留数据加载器(即发电机)时才可能实现。因此,当使用
    list(dataloader)
    时,转换是在运行时对输入数据进行计算的,而不是在编译时(如果愿意的话)



    我建议您让您的
    数据集
    为每个项目生成非缓冲序列,然后使用
    shuffle=True
    从中生成一个
    DataLoader
    。这感觉比生成一个
    数据加载程序
    只编译下来要自然得多。按预期使用dataset类。它应该是构造每个序列(即数据点)的序列,或者说它是一个“单个观察对象”。

    您能解释一下这样做的效用吗?在处理时间相关数据(视频片段)时很有用,您希望在相邻帧之间共享数据。我认为,与完全非缓冲的数据集相比,这种方法应该可以减少过度拟合,因为在这种情况下,模型可以只学习顺序。在这种情况下,每个序列形成一个单独的观察对象,不易受到洗牌的影响。已经建立了时间序列模型来处理这个问题。问题似乎是如何重新发明这个轮子。那么,什么是更好的方法呢?当我将DataLoader的shuffle参数设置为True时,这将洗牌minibacks中的所有数据。原谅我的无知;我学Pytork才半年。