docstr: :param bert_inputs: [B, L']
  :param grid_mask2d: [B, L, L]
  :param dist_inputs: [B, L, L]
  :param pieces2word: [B, L, L']
  :param sent_length: [B]
  :return:
docstr_tok: [":","param","bert_inputs",":","[","B",",","L","'","]",":","param","grid_mask2d",":","[","B",",","L",",","L","]",":","param","dist_inputs",":","[","B",",","L",",","L","]",":","param","pieces2word",":","[","B",",","L",",","L","'","]",":","param","sent_length",":","[","B","]",":","return",":"]
code: def forward(
      self,
      bert_inputs,
      grid_mask2d,
      dist_inputs,
      pieces2word,
      sent_length,
  ):
      """
      :param bert_inputs: [B, L']
      :param grid_mask2d: [B, L, L]
      :param dist_inputs: [B, L, L]
      :param pieces2word: [B, L, L']
      :param sent_length: [B]
      :return:
      """
      bert_embs = self.bert(
          input_ids=bert_inputs,
          attention_mask=bert_inputs.ne(0).float(),
      )
      if self.use_bert_last_4_layers:
          bert_embs = torch.stack(bert_embs[2][-4:], dim=-1).mean(-1)
      else:
          bert_embs = bert_embs[0]
  
      length = pieces2word.size(1)
  
      min_value = torch.min(bert_embs).item()
  
      # Max pooling word representations from pieces
      _bert_embs = bert_embs.unsqueeze(1).expand(-1, length, -1, -1)
      _bert_embs = torch.masked_fill(
          _bert_embs, pieces2word.eq(0).unsqueeze(-1), min_value
      )
      word_reps, _ = torch.max(_bert_embs, dim=2)
  
      word_reps = self.dropout(word_reps)
      packed_embs = pack_padded_sequence(
          word_reps,
          sent_length.cpu(),
          batch_first=True,
          enforce_sorted=False,
      )
      packed_outs, (hidden, _) = self.encoder(packed_embs)
      word_reps, _ = pad_packed_sequence(
          packed_outs, batch_first=True, total_length=sent_length.max()
      )
  
      cln = self.cln(word_reps.unsqueeze(2), word_reps)
  
      dis_emb = self.dis_embs(dist_inputs)
      tril_mask = torch.tril(grid_mask2d.clone().long())
      reg_inputs = tril_mask + grid_mask2d.clone().long()
      reg_emb = self.reg_embs(reg_inputs)
  
      conv_inputs = torch.cat([dis_emb, reg_emb, cln], dim=-1)
      conv_inputs = torch.masked_fill(
          conv_inputs, grid_mask2d.eq(0).unsqueeze(-1), 0.0
      )
      conv_outputs = self.convLayer(conv_inputs)
      conv_outputs = torch.masked_fill(
          conv_outputs, grid_mask2d.eq(0).unsqueeze(-1), 0.0
      )
      outputs = self.predictor(word_reps, word_reps, conv_outputs)
  
      return outputs
  
imports: import torch
  import torch.nn
  import torch.nn.functional
  from torch.nn.utils.rnn import pack_padded_sequence, pad_packed_sequence
  from transformers import AutoModel
label_desc: Use image node_id 2 for calling the Model obj's underlying member method code with example usage: obj.forward(bert_inputs, grid_mask2d, dist_inputs, pieces2word, sent_length) and returns: outputs