zczcwh / PoseFormer

The project is an official implementation of our paper "3D Human Pose Estimation with Spatial and Temporal Transformers".
498 stars 73 forks source link

about GPU memory required ? #20

Open vicentowang opened 3 years ago

vicentowang commented 3 years ago

my single GPU with 16G memory, get "CUDA out of memory" . can I use cpu to run the code ?

vicentowang commented 3 years ago

I change the batch_size config for evaluation. solve the problem. thanks anyway.

Astralex98 commented 3 years ago

Hi, @vicentowang

I got the same problem as you. Can you, please, say, where did you find batch_size for evaluation? Seems to me that batch size in arguments is not related to evaluation.

Thanks!

vicentowang commented 3 years ago

Hi, @vicentowang

I got the same problem as you. Can you, please, say, where did you find batch_size for evaluation? Seems to me that batch size in arguments is not related to evaluation.

Thanks!

add code in run_poseformer.py evaluate() function to solve this problem with args.batch_size=512, args.works=0:

        torch_dataset = Data.TensorDataset(inputs_2d, inputs_2d_flip)
        loader = Data.DataLoader(dataset=torch_dataset, batch_size=args.batch_size, 
                                 shuffle=False, num_workers=args.works)

        predicted_3d_pos_x = []
        predicted_3d_pos_flip_x = []
        for step, (batch_inputs_2d, batch_inputs_2d_flip) in enumerate(loader):
            predicted_3d_pos_x.append(model_pos(batch_inputs_2d))
            predicted_3d_pos_flip_x.append(model_pos(batch_inputs_2d_flip))

        predicted_3d_pos = torch.cat(predicted_3d_pos_x, dim=0)
        predicted_3d_pos_flip = torch.cat(predicted_3d_pos_flip_x, dim=0)
Astralex98 commented 3 years ago

Thank you for your answer, @vicentowang

  1. Can you. please, say, where exactly should I put your code in the evaluate function? It would be great if you could tell the lines in the run_poseformer.py function where to put your code.

  2. Besides putting your code, should I remove or correct some code in run_poseformer.py?

Thanks in advance!

vicentowang commented 3 years ago

def evaluate(test_generator, action=None, return_predictions=False, use_trajectory_model=False): epoch_loss_3d_pos = 0 epoch_loss_3d_pos_procrustes = 0 epoch_loss_3d_pos_scale = 0 epoch_loss_3d_vel = 0 with torch.no_grad(): if not use_trajectory_model: model_pos.eval()

else:

        # model_traj.eval()
    N = 0
    for _, batch, batch_2d in test_generator.next_epoch():
        batch = batch_2d
        inputs_2d = torch.from_numpy(batch_2d.astype('float32'))
        inputs_3d = torch.from_numpy(batch.astype('float32'))

        ##### apply test-time-augmentation (following Videopose3d)
        inputs_2d_flip = inputs_2d.clone()
        inputs_2d_flip [:, :, :, 0] *= -1
        inputs_2d_flip[:, :, kps_left + kps_right,:] = inputs_2d_flip[:, :, kps_right + kps_left,:]

        ##### convert size
        inputs_2d, inputs_3d = eval_data_prepare(receptive_field, inputs_2d, inputs_3d)
        inputs_2d_flip, _ = eval_data_prepare(receptive_field, inputs_2d_flip, inputs_3d)

        if torch.cuda.is_available():
            inputs_2d = inputs_2d.cuda()
            inputs_2d_flip = inputs_2d_flip.cuda()
            inputs_3d = inputs_3d.cuda()
        inputs_3d[:, :, 0] = 0

        torch_dataset = Data.TensorDataset(inputs_2d, inputs_2d_flip)
        loader = Data.DataLoader(dataset=torch_dataset, batch_size=args.batch_size, 
                                 shuffle=False, num_workers=args.works)

        predicted_3d_pos_x = []
        predicted_3d_pos_flip_x = []
        for step, (batch_inputs_2d, batch_inputs_2d_flip) in enumerate(loader):
            predicted_3d_pos_x.append(model_pos(batch_inputs_2d))
            predicted_3d_pos_flip_x.append(model_pos(batch_inputs_2d_flip))

        predicted_3d_pos = torch.cat(predicted_3d_pos_x, dim=0)
        predicted_3d_pos_flip = torch.cat(predicted_3d_pos_flip_x, dim=0)
        predicted_3d_pos_flip[:, :, :, 0] *= -1
        predicted_3d_pos_flip[:, :, joints_left + joints_right] = predicted_3d_pos_flip[:, :, joints_right + joints_left]
        predicted_3d_pos = torch.mean(torch.cat((predicted_3d_pos, predicted_3d_pos_flip), dim=1), dim=1, keepdim=True)

        del inputs_2d, inputs_2d_flip
        torch.cuda.empty_cache()

        if return_predictions:
            return predicted_3d_pos.squeeze(1).cpu().numpy()

        error = mpjpe(predicted_3d_pos, inputs_3d)
        epoch_loss_3d_pos_scale += inputs_3d.shape[0]*inputs_3d.shape[1] * n_mpjpe(predicted_3d_pos, inputs_3d).item()

        epoch_loss_3d_pos += inputs_3d.shape[0]*inputs_3d.shape[1] * error.item()
        N += inputs_3d.shape[0] * inputs_3d.shape[1]

        inputs = inputs_3d.cpu().numpy().reshape(-1, inputs_3d.shape[-2], inputs_3d.shape[-1])
        predicted_3d_pos = predicted_3d_pos.cpu().numpy().reshape(-1, inputs_3d.shape[-2], inputs_3d.shape[-1])

        epoch_loss_3d_pos_procrustes += inputs_3d.shape[0]*inputs_3d.shape[1] * p_mpjpe(predicted_3d_pos, inputs)

        # Compute velocity error
        epoch_loss_3d_vel += inputs_3d.shape[0]*inputs_3d.shape[1] * mean_velocity_error(predicted_3d_pos, inputs)

if action is None:
    print('----------')
else:
    print('----'+action+'----')
e1 = (epoch_loss_3d_pos / N)*1000
e2 = (epoch_loss_3d_pos_procrustes / N)*1000
e3 = (epoch_loss_3d_pos_scale / N)*1000
ev = (epoch_loss_3d_vel / N)*1000
print('Protocol #1 Error (MPJPE):', e1, 'mm')
print('Protocol #2 Error (P-MPJPE):', e2, 'mm')
print('Protocol #3 Error (N-MPJPE):', e3, 'mm')
print('Velocity Error (MPJVE):', ev, 'mm')
print('----------')

return e1, e2, e3, ev
Astralex98 commented 3 years ago

Thank you very much! It is working now!

Yinhappy commented 2 years ago

Hello! @vicentowang @Astralex98 I set the same code, but there were some problems.

Traceback (most recent call last): File "run_poseformer.py", line 802, in run_evaluation(all_actions, action_filter) File "run_poseformer.py", line 789, in run_evaluation e1, e2, e3, ev = evaluate(gen, action_key) File "run_poseformer.py", line 634, in evaluate error = mpjpe(predicted_3d_pos, inputs_3d) File "/data/PoseFormer-main/common/loss.py", line 16, in mpjpe assert predicted.shape == target.shape AssertionError