Cannot enumerate over Dataloader object

Abbas_Jariani: <p>Hi,</p>
<p>I am trying to setup a fully convolutional network for segmentation of my microscopy images (<a href="https://www.dropbox.com/s/gr65893vbr67zyp/my_train_valid_set.rar?dl=0" class="inline-onebox" rel="noopener nofollow ugc">Dropbox - Error - Simplify your life</a>). For each image I have the binary mask as well as the raw image from the microscope. I have only one class for the images, and I am only interested in pixel segmentation.</p>
<p>I understand that for loading my own dataset I need to create a custom  <code>torch.utils.data.dataset</code> class. So I made an attempt on this. Then I proceeded with making the <code>torch.utils.data.DataLoader</code> object from this class. I make my model based on <a href="https://github.com/wkentaro/pytorch-fcn" class="inline-onebox" rel="noopener nofollow ugc">GitHub - wkentaro/pytorch-fcn: PyTorch Implementation of Fully Convolutional Networks. (Training code to reproduce the original result is available.)</a>. I noticed that when I start training my model, the progress gets stuck at 0%. When I looked into why this is, I realized that for some reason when I try to run a loop (for or enumerate) over my <code>DataLoader</code> objects (<code>train_loader</code>, <code>val_loader</code>), the scripts gets stuck. I wonder if anyone can help me what am I doing wrong here? Thank you very much!</p>
<p>Abbas Jariani</p>
<blockquote>
<p>import datetime<br>
import os<br>
import os.path as osp<br>
import fcn<br>
import numpy as np<br>
import torch<br>
import torch.nn as nn<br>
<span class="hashtag-raw">#import</span> torchfcn<br>
import torchvision<br>
##################################<br>
<span class="hashtag-raw">#import</span> datetime<br>
from distutils.version import LooseVersion<br>
import math<br>
<span class="hashtag-raw">#import</span> os<br>
<span class="hashtag-raw">#import</span> os.path as osp<br>
import shutil<br>
import pytz<br>
import scipy.misc<br>
from torch.autograd import Variable<br>
import torch.nn.functional as F<br>
import tqdm<br>
import random<br>
from PIL import Image<br>
import torch.utils.data as utils_data<br>
###################################</p>
<p>def get_upsampling_weight(in_channels, out_channels, kernel_size):<br>
“”“Make a 2D bilinear kernel suitable for upsampling”“”<br>
factor = (kernel_size + 1) // 2<br>
if kernel_size % 2 == 1:<br>
center = factor - 1<br>
else:<br>
center = factor - 0.5<br>
og = np.ogrid[:kernel_size, :kernel_size]<br>
filt = (1 - abs(og[0] - center) / factor) * <br>
(1 - abs(og[1] - center) / factor)<br>
weight = np.zeros((in_channels, out_channels, kernel_size, kernel_size),<br>
dtype=np.float64)<br>
weight[range(in_channels), range(out_channels), :, :] = filt<br>
return torch.from_numpy(weight).float()</p>
<p>class FCN32s(nn.Module):</p>
<pre><code>pretrained_model = \
    osp.expanduser('~/data/models/pytorch/fcn32s_from_caffe.pth')

@classmethod
def download(cls):
    return fcn.data.cached_download(
        url='http://drive.google.com/uc?id=0B9P1L--7Wd2vM2oya3k0Zlgtekk',
        path=cls.pretrained_model,
        md5='8acf386d722dc3484625964cbe2aba49',
    )

def __init__(self, n_class=21):
    super(FCN32s, self).__init__()
    # conv1
    self.conv1_1 = nn.Conv2d(3, 64, 3, padding=100)
    self.relu1_1 = nn.ReLU(inplace=True)
    self.conv1_2 = nn.Conv2d(64, 64, 3, padding=1)
    self.relu1_2 = nn.ReLU(inplace=True)
    self.pool1 = nn.MaxPool2d(2, stride=2, ceil_mode=True)  # 1/2

    # conv2
    self.conv2_1 = nn.Conv2d(64, 128, 3, padding=1)
    self.relu2_1 = nn.ReLU(inplace=True)
    self.conv2_2 = nn.Conv2d(128, 128, 3, padding=1)
    self.relu2_2 = nn.ReLU(inplace=True)
    self.pool2 = nn.MaxPool2d(2, stride=2, ceil_mode=True)  # 1/4

    # conv3
    self.conv3_1 = nn.Conv2d(128, 256, 3, padding=1)
    self.relu3_1 = nn.ReLU(inplace=True)
    self.conv3_2 = nn.Conv2d(256, 256, 3, padding=1)
    self.relu3_2 = nn.ReLU(inplace=True)
    self.conv3_3 = nn.Conv2d(256, 256, 3, padding=1)
    self.relu3_3 = nn.ReLU(inplace=True)
    self.pool3 = nn.MaxPool2d(2, stride=2, ceil_mode=True)  # 1/8

    # conv4
    self.conv4_1 = nn.Conv2d(256, 512, 3, padding=1)
    self.relu4_1 = nn.ReLU(inplace=True)
    self.conv4_2 = nn.Conv2d(512, 512, 3, padding=1)
    self.relu4_2 = nn.ReLU(inplace=True)
    self.conv4_3 = nn.Conv2d(512, 512, 3, padding=1)
    self.relu4_3 = nn.ReLU(inplace=True)
    self.pool4 = nn.MaxPool2d(2, stride=2, ceil_mode=True)  # 1/16

    # conv5
    self.conv5_1 = nn.Conv2d(512, 512, 3, padding=1)
    self.relu5_1 = nn.ReLU(inplace=True)
    self.conv5_2 = nn.Conv2d(512, 512, 3, padding=1)
    self.relu5_2 = nn.ReLU(inplace=True)
    self.conv5_3 = nn.Conv2d(512, 512, 3, padding=1)
    self.relu5_3 = nn.ReLU(inplace=True)
    self.pool5 = nn.MaxPool2d(2, stride=2, ceil_mode=True)  # 1/32

    # fc6
    self.fc6 = nn.Conv2d(512, 4096, 7)
    self.relu6 = nn.ReLU(inplace=True)
    self.drop6 = nn.Dropout2d()

    # fc7
    self.fc7 = nn.Conv2d(4096, 4096, 1)
    self.relu7 = nn.ReLU(inplace=True)
    self.drop7 = nn.Dropout2d()

    self.score_fr = nn.Conv2d(4096, n_class, 1)
    self.upscore = nn.ConvTranspose2d(n_class, n_class, 64, stride=32,
                                      bias=False)

    self._initialize_weights()

def _initialize_weights(self):
    for m in self.modules():
        if isinstance(m, nn.Conv2d):
            m.weight.data.zero_()
            if m.bias is not None:
                m.bias.data.zero_()
        if isinstance(m, nn.ConvTranspose2d):
            assert m.kernel_size[0] == m.kernel_size[1]
            initial_weight = get_upsampling_weight(
                m.in_channels, m.out_channels, m.kernel_size[0])
            m.weight.data.copy_(initial_weight)

def forward(self, x):
    h = x
    h = self.relu1_1(self.conv1_1(h))
    h = self.relu1_2(self.conv1_2(h))
    h = self.pool1(h)

    h = self.relu2_1(self.conv2_1(h))
    h = self.relu2_2(self.conv2_2(h))
    h = self.pool2(h)

    h = self.relu3_1(self.conv3_1(h))
    h = self.relu3_2(self.conv3_2(h))
    h = self.relu3_3(self.conv3_3(h))
    h = self.pool3(h)

    h = self.relu4_1(self.conv4_1(h))
    h = self.relu4_2(self.conv4_2(h))
    h = self.relu4_3(self.conv4_3(h))
    h = self.pool4(h)

    h = self.relu5_1(self.conv5_1(h))
    h = self.relu5_2(self.conv5_2(h))
    h = self.relu5_3(self.conv5_3(h))
    h = self.pool5(h)

    h = self.relu6(self.fc6(h))
    h = self.drop6(h)

    h = self.relu7(self.fc7(h))
    h = self.drop7(h)

    h = self.score_fr(h)

    h = self.upscore(h)
    h = h[:, :, 19:19 + x.size()[2], 19:19 + x.size()[3]].contiguous()

    return h

def copy_params_from_vgg16(self, vgg16):
    features = [
        self.conv1_1, self.relu1_1,
        self.conv1_2, self.relu1_2,
        self.pool1,
        self.conv2_1, self.relu2_1,
        self.conv2_2, self.relu2_2,
        self.pool2,
        self.conv3_1, self.relu3_1,
        self.conv3_2, self.relu3_2,
        self.conv3_3, self.relu3_3,
        self.pool3,
        self.conv4_1, self.relu4_1,
        self.conv4_2, self.relu4_2,
        self.conv4_3, self.relu4_3,
        self.pool4,
        self.conv5_1, self.relu5_1,
        self.conv5_2, self.relu5_2,
        self.conv5_3, self.relu5_3,
        self.pool5,
    ]
    for l1, l2 in zip(vgg16.features, features):
        if isinstance(l1, nn.Conv2d) and isinstance(l2, nn.Conv2d):
            assert l1.weight.size() == l2.weight.size()
            assert l1.bias.size() == l2.bias.size()
            l2.weight.data = l1.weight.data
            l2.bias.data = l1.bias.data
    for i, name in zip([0, 3], ['fc6', 'fc7']):
        l1 = vgg16.classifier[i]
        l2 = getattr(self, name)
        l2.weight.data = l1.weight.data.view(l2.weight.size())
        l2.bias.data = l1.bias.data.view(l2.bias.size())
</code></pre>
<p>##################################################<br>
def _fast_hist(label_true, label_pred, n_class):<br>
mask = (label_true &gt;= 0) &amp; (label_true &lt; n_class)<br>
hist = np.bincount(<br>
n_class * label_true[mask].astype(int) +<br>
label_pred[mask], minlength=n_class ** 2).reshape(n_class, n_class)<br>
return hist</p>
<p>def label_accuracy_score(label_trues, label_preds, n_class):<br>
“”"Returns accuracy score evaluation result.</p>
<pre><code>  - overall accuracy
  - mean accuracy
  - mean IU
  - fwavacc
"""
hist = np.zeros((n_class, n_class))
for lt, lp in zip(label_trues, label_preds):
    hist += _fast_hist(lt.flatten(), lp.flatten(), n_class)
acc = np.diag(hist).sum() / hist.sum()
with np.errstate(divide='ignore', invalid='ignore'):
    acc_cls = np.diag(hist) / hist.sum(axis=1)
acc_cls = np.nanmean(acc_cls)
with np.errstate(divide='ignore', invalid='ignore'):
    iu = np.diag(hist) / (
        hist.sum(axis=1) + hist.sum(axis=0) - np.diag(hist)
    )
mean_iu = np.nanmean(iu)
freq = hist.sum(axis=1) / hist.sum()
fwavacc = (freq[freq &gt; 0] * iu[freq &gt; 0]).sum()
return acc, acc_cls, mean_iu, fwavacc
</code></pre>
<p>def cross_entropy2d(input, target, weight=None, size_average=True):<br>
# input: (n, c, h, w), target: (n, h, w)<br>
n, c, h, w = input.size()<br>
# log_p: (n, c, h, w)<br>
if LooseVersion(torch.<strong>version</strong>) &lt; LooseVersion(‘0.3’):<br>
# ==0.2.X<br>
log_p = F.log_softmax(input)<br>
else:<br>
# &gt;=0.3<br>
log_p = F.log_softmax(input, dim=1)<br>
# log_p: (n<em>h</em>w, c)<br>
log_p = log_p.transpose(1, 2).transpose(2, 3).contiguous()<br>
log_p = log_p[target.view(n, h, w, 1).repeat(1, 1, 1, c) &gt;= 0]<br>
log_p = log_p.view(-1, c)<br>
# target: (n<em>h</em>w,)<br>
mask = target &gt;= 0<br>
target = target[mask]<br>
loss = F.nll_loss(log_p, target, weight=weight, reduction=‘sum’)<br>
if size_average:<br>
loss /= mask.data.sum()<br>
return loss</p>
<p>class Trainer(object):</p>
<pre><code>def __init__(self, cuda, model, optimizer,
             train_loader, val_loader, out, max_iter,
             size_average=False, interval_validate=None):
    self.cuda = cuda

    self.model = model
    self.optim = optimizer

    self.train_loader = train_loader
    self.val_loader = val_loader

    self.timestamp_start = \
        datetime.datetime.now(pytz.timezone('Asia/Tokyo'))
    self.size_average = size_average

    if interval_validate is None:
        self.interval_validate = len(self.train_loader)
    else:
        self.interval_validate = interval_validate

    self.out = out
    if not osp.exists(self.out):
        os.makedirs(self.out)

    self.log_headers = [
        'epoch',
        'iteration',
        'train/loss',
        'train/acc',
        'train/acc_cls',
        'train/mean_iu',
        'train/fwavacc',
        'valid/loss',
        'valid/acc',
        'valid/acc_cls',
        'valid/mean_iu',
        'valid/fwavacc',
        'elapsed_time',
    ]
    if not osp.exists(osp.join(self.out, 'log.csv')):
        with open(osp.join(self.out, 'log.csv'), 'w') as f:
            f.write(','.join(self.log_headers) + '\n')

    self.epoch = 0
    self.iteration = 0
    self.max_iter = max_iter
    self.best_mean_iu = 0

def validate(self):
    training = self.model.training
    self.model.eval()

    n_class = len(self.val_loader.dataset.class_names)

    val_loss = 0
    visualizations = []
    label_trues, label_preds = [], []
    for batch_idx, (data, target) in tqdm.tqdm(
            enumerate(self.val_loader), total=len(self.val_loader),
            desc='Valid iteration=%d' % self.iteration, ncols=80,
            leave=False):
        if self.cuda:
            data, target = data.cuda(), target.cuda()
        data, target = Variable(data), Variable(target)
        with torch.no_grad():
            score = self.model(data)

        loss = cross_entropy2d(score, target,
                               size_average=self.size_average)
        loss_data = loss.data.item()
        if np.isnan(loss_data):
            raise ValueError('loss is nan while validating')
        val_loss += loss_data / len(data)

        imgs = data.data.cpu()
        lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :]
        lbl_true = target.data.cpu()
        for img, lt, lp in zip(imgs, lbl_true, lbl_pred):
            img, lt = self.val_loader.dataset.untransform(img, lt)
            label_trues.append(lt)
            label_preds.append(lp)
            if len(visualizations) &lt; 9:
                viz = fcn.utils.visualize_segmentation(
                    lbl_pred=lp, lbl_true=lt, img=img, n_class=n_class)
                visualizations.append(viz)
    metrics = label_accuracy_score(
        label_trues, label_preds, n_class)

    out = osp.join(self.out, 'visualization_viz')
    if not osp.exists(out):
        os.makedirs(out)
    out_file = osp.join(out, 'iter%012d.jpg' % self.iteration)
    scipy.misc.imsave(out_file, fcn.utils.get_tile_image(visualizations))

    val_loss /= len(self.val_loader)

    with open(osp.join(self.out, 'log.csv'), 'a') as f:
        elapsed_time = (
            datetime.datetime.now(pytz.timezone('Asia/Tokyo')) -
            self.timestamp_start).total_seconds()
        log = [self.epoch, self.iteration] + [''] * 5 + \
              [val_loss] + list(metrics) + [elapsed_time]
        log = map(str, log)
        f.write(','.join(log) + '\n')

    mean_iu = metrics[2]
    is_best = mean_iu &gt; self.best_mean_iu
    if is_best:
        self.best_mean_iu = mean_iu
    torch.save({
        'epoch': self.epoch,
        'iteration': self.iteration,
        'arch': self.model.__class__.__name__,
        'optim_state_dict': self.optim.state_dict(),
        'model_state_dict': self.model.state_dict(),
        'best_mean_iu': self.best_mean_iu,
    }, osp.join(self.out, 'checkpoint.pth.tar'))
    if is_best:
        shutil.copy(osp.join(self.out, 'checkpoint.pth.tar'),
                    osp.join(self.out, 'model_best.pth.tar'))

    if training:
        self.model.train()

def train_epoch(self):
    self.model.train()

    n_class = len(self.train_loader.dataset.class_names)


    #print("XXXXX")
    #print(list(enumerate((self.train_loader)) ))
    #print("XXXXX")
    for batch_idx, (data, target) in tqdm.tqdm(
            enumerate(self.train_loader), total=len(self.train_loader),
            desc='Train epoch=%d' % self.epoch, ncols=80, leave=False):
        
        iteration = batch_idx + self.epoch * len(self.train_loader)
        
        if self.iteration != 0 and (iteration - 1) != self.iteration:
            continue  # for resuming
        self.iteration = iteration

        if self.iteration % self.interval_validate == 0:
            self.validate()

        assert self.model.training

        if self.cuda:
            data, target = data.cuda(), target.cuda()
        data, target = Variable(data), Variable(target)
        ###############
        #
        #print(type(data))
        #print(type(target))
        #print("XXXXXX")
        #########
        self.optim.zero_grad()
        score = self.model(data)

        loss = cross_entropy2d(score, target,
                               size_average=self.size_average)
        loss /= len(data)
        loss_data = loss.data.item()
        if np.isnan(loss_data):
            raise ValueError('loss is nan while training')
        loss.backward()
        self.optim.step()

        metrics = []
        lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :]
        lbl_true = target.data.cpu().numpy()
        acc, acc_cls, mean_iu, fwavacc = \
            label_accuracy_score(
                lbl_true, lbl_pred, n_class=n_class)
        metrics.append((acc, acc_cls, mean_iu, fwavacc))
        metrics = np.mean(metrics, axis=0)

        with open(osp.join(self.out, 'log.csv'), 'a') as f:
            elapsed_time = (
                datetime.datetime.now(pytz.timezone('Asia/Tokyo')) -
                self.timestamp_start).total_seconds()
            log = [self.epoch, self.iteration] + [loss_data] + \
                metrics.tolist() + [''] * 5 + [elapsed_time]
            log = map(str, log)
            f.write(','.join(log) + '\n')

        if self.iteration &gt;= self.max_iter:
            break

def train(self):
    max_epoch = int(math.ceil(1. * self.max_iter / len(self.train_loader)))

    
    for epoch in tqdm.trange(self.epoch, max_epoch,
                             desc='Train', ncols=80):
        self.epoch = epoch
        self.train_epoch()
        if self.iteration &gt;= self.max_iter:
            break
</code></pre>
<p>def get_parameters(model, bias=False):<br>
import torch.nn as nn<br>
modules_skipped = (<br>
nn.ReLU,<br>
nn.MaxPool2d,<br>
nn.Dropout2d,<br>
nn.Sequential,<br>
FCN32s,<br>
<span class="hashtag-raw">#torchfcn</span>.models.FCN16s,<br>
<span class="hashtag-raw">#torchfcn</span>.models.FCN8s,<br>
)<br>
for m in model.modules():<br>
if isinstance(m, nn.Conv2d):<br>
if bias:<br>
yield m.bias<br>
else:<br>
yield m.weight<br>
elif isinstance(m, nn.ConvTranspose2d):<br>
# weight is frozen because it is just a bilinear upsampling<br>
if bias:<br>
assert m.bias is None<br>
elif isinstance(m, modules_skipped):<br>
continue<br>
else:<br>
raise ValueError(‘Unexpected module: %s’ % str(m))</p>
<p>class MyDataSet(utils_data.Dataset):<br>
def <strong>init</strong>(self, root_dir, image_dir, mask_dir, label, transform=None):<br>
self.dataset_path = root_dir<br>
self.image_dir = image_dir<br>
self.mask_dir = os.path.join(mask_dir, label)<br>
self.transform = transform<br>
mask_full_path = os.path.join(self.dataset_path, self.mask_dir)<br>
self.mask_file_list = [f for f in os.listdir(mask_full_path) if osp.isfile(osp.join(mask_full_path, f))]<br>
random.shuffle(self.mask_file_list)<br>
self.class_names = [‘1’]</p>
<p>def <strong>getitem</strong>(self, index):<br>
file_name =  self.mask_file_list[index].rsplit(‘.’, 1)[0]<br>
img_name = os.path.join(self.dataset_path, self.image_dir, file_name+‘.jpg’)<br>
mask_name = os.path.join(self.dataset_path, self.mask_dir, self.mask_file_list[index])<br>
image = Image.open(img_name)<br>
mask = Image.open(mask_name)<br>
image = np.array(image)<br>
image = np.rollaxis(image, 2, 0)<br>
image = np.array(image).astype(np.float32)<br>
labels = np.array(mask).astype(np.uint8)<br>
sample = {‘image’: image, ‘labels’: labels}</p>
<pre><code>  if self.transform:
      sample = self.transform(sample)

  return sample
</code></pre>
<p>def <strong>len</strong>(self):<br>
return len(self.mask_file_list)</p>
<p>normalize = torchvision.transforms.Normalize(mean=1, std= 0.3)<br>
transform_pipeline = torchvision.transforms.Compose([<br>
<span class="hashtag-raw">#torchvision</span>.transforms.RandomResizedCrop(12),<br>
torchvision.transforms.RandomHorizontalFlip(),<br>
torchvision.transforms.ToTensor(),<br>
<span class="hashtag-raw">#normalize</span>,<br>
])</p>
<p><span class="hashtag-raw">#mask_dir</span> = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\curated_masks_from_oline’<br>
<span class="hashtag-raw">#tritc_dir</span> = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\curated_tritc_from_oline’</p>
<p>train_tritc = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\train_tritc\’<br>
train_masks = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\train_masks\’<br>
valid_tritc = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\valid_tritc\’<br>
valid_masks = ‘\\Moana\oc1\OcellO Projects\VitroScan\190430_create_trainset_deepl\OVCA2018_08\valid_masks\’<br>
<span class="hashtag-raw">#train_data</span> = MyDataSet( args.traindir, args.image_dir, args.mask_dir, args.label)</p>
<p>train_data = MyDataSet( ‘D:\myTools\pytorch-fcn-master\examples\voc\out_FCN32s’, train_tritc, train_masks, ‘1’)<br>
valid_data = MyDataSet( ‘D:\myTools\pytorch-fcn-master\examples\voc\out_FCN32s’, valid_tritc, valid_masks, ‘1’)</p>
<p><span class="hashtag-raw">#sampler_train</span> = DummySampler(train_data)<br>
<span class="hashtag-raw">#sampler_valid</span> = DummySampler(valid_data)</p>
<p>train_loader = torch.utils.data.DataLoader( train_data,<br>
batch_size=1, shuffle=False,<br>
num_workers=5, pin_memory=True)</p>
<p>val_loader = torch.utils.data.DataLoader( valid_data,<br>
batch_size=1, shuffle=False,<br>
num_workers=5, pin_memory=True)</p>
<p>################################</p>
<p>model = FCN32s(n_class=1)<br>
<span class="hashtag-raw">#model</span> = torchfcn.models.FCN8s(n_class=1)<br>
<span class="hashtag-raw">#vgg16</span> = torchfcn.models.VGG16(pretrained=True)<br>
<span class="hashtag-raw">#model</span>.copy_params_from_vgg16(vgg16)<br>
model = model.cuda()</p>
<p>optim = torch.optim.SGD(<br>
[<br>
{‘params’: get_parameters(model, bias=False)},<br>
{‘params’: get_parameters(model, bias=True),<br>
‘lr’: 1.0e-10 * 2, ‘weight_decay’: 0},<br>
],<br>
lr=1.0e-10,<br>
momentum=0.99,<br>
weight_decay=0.0005)</p>
<p>trainer = Trainer(<br>
cuda=True,<br>
model=model,<br>
optimizer=optim,<br>
train_loader=train_loader,<br>
val_loader=val_loader,<br>
out=‘D:\myTools\pytorch-fcn-master\examples\voc\out_FCN32s’,<br>
max_iter=10000,<br>
interval_validate=4000,<br>
)</p>
<p>start_epoch = 0<br>
start_iteration = 0<br>
trainer.epoch = start_epoch<br>
trainer.iteration = start_iteration</p>
<p>##################<br>
deviceid = 0<br>
os.environ[‘CUDA_VISIBLE_DEVICES’] = “%d”%deviceid</p>
<p>################<br>
trainer.train()</p>
</blockquote>

ptrblck: <p>Is your code running fine using <code>num_workers=0</code>?<br>
If you are using multiple workers on Windows, you should add the if-clause protection as described in the <a href="https://pytorch.org/docs/stable/notes/windows.html#usage-multiprocessing" rel="nofollow noopener">Windows FAQ</a>.</p>

Abbas_Jariani: <p>Wow, that solved the issue, thanks!</p>

FiReTiTi: <p>It also happened to me on MacOS.<br>
A student reported the same issue on Ubuntu.<br>
Anyway, the workaround worked every time.</p>