def predict(
        self,
        images: torch.Tensor,
        data_samples: Optional[List[DataSample]] = None,
    ):
        """update data_samples that contain pred_answer for each question.

        Args:
            images (Tensor): A batch of images. The shape of it should be
                (B, C, H, W) for images and (B, T, C, H, W) for videos.
            data_samples (List[DataSample], optional): The annotation
                data of every samples.

        Returns:
            Dict[torch.Tensor]: The losses features.
        """
        visual_embeds = self.extract_feat(images)
        image_atts = torch.ones(
            visual_embeds.size()[:-1], dtype=torch.long).to(self.device)

        questions = []
        for sample in data_samples:
            questions.append(sample.get('question'))
        questions = self.tokenizer(
            questions, padding='longest', return_tensors='pt').to(self.device)

        questions.input_ids[:, 0] = \
            self.tokenizer.additional_special_tokens_ids[0]

        # multimodal fusion
        multimodal_embeds = self.multimodal_backbone(
            questions.input_ids,
            attention_mask=questions.attention_mask,
            encoder_hidden_states=visual_embeds,
            encoder_attention_mask=image_atts,
            return_dict=True,
        )

        if self.vqa_head.inference_method == 'rank':
            answer_candidates = self.tokenizer(
                self.vqa_head.answer_list,
                padding='longest',
                return_tensors='pt').to(self.device)
            answer_candidates.input_ids[:, 0] = self.tokenizer.bos_token_id
        elif self.vqa_head.inference_method == 'generate':
            answer_candidates = None

        head_feats = dict(
            multimodal_embeds=multimodal_embeds.last_hidden_state,
            question_atts=questions.attention_mask,
            answer_candidates=answer_candidates,
            bos_token_id=self.tokenizer.bos_token_id,
            sep_token_id=self.tokenizer.sep_token_id,
            pad_token_id=self.tokenizer.pad_token_id,
        )

        if self.vqa_head.inference_method == 'rank':
            answers = self.vqa_head.predict(head_feats)
            for answer, data_sample in zip(answers, data_samples):
                data_sample.pred_answer = answer

        elif self.vqa_head.inference_method == 'generate':
            outputs = self.vqa_head.predict(head_feats)
            for output, data_sample in zip(outputs, data_samples):
                data_sample.pred_answer = self.tokenizer.decode(
                    output, skip_special_tokens=True)

        return data_samples
update data_samples that contain pred_answer for each question.

        Args:
            images (Tensor): A batch of images. The shape of it should be
                (B, C, H, W) for images and (B, T, C, H, W) for videos.
            data_samples (List[DataSample], optional): The annotation
                data of every samples.

        Returns:
            Dict[torch.Tensor]: The losses features.
        
mmpretrain/models/multimodal/blip/blip_vqa.py