You want batch_size=16, but you can only fit 8 images images in your memory: then you will accumulate the gradients for two mini batches of size 8, and perform the optimization step every two iterations (2*8 = 16). Your code would look something like this:
dataloader = DataLoader(.., batch_size=8, ..)

for i, (minibatch, labels) in enumerate(dataloader):
  output = model(minibatch)
  loss = criterion(output, labels)
  loss.backward()

  if (i+1) % 2 == 0:
    optimizer.step()
    optimizer.zero_grad()