code: def on_validation_epoch_end(self):
      prefix = "test" if self.trainer.testing else "val"
  
      if prefix == "val":
          loss_terms = [
              x[f"{prefix}_loss"] for x in self.validation_step_outputs
          ]
          (
              generated_answers,
              unique_ids,
              per_sample_perplexity,
          ) = QAMetrics.convert_dict_outputs_to_lists(
              self.validation_step_outputs,
              [
                  "generated_answers",
                  "unique_ids",
                  "per_sample_perplexity",
              ],
          )
          self.validation_step_outputs.clear()  # free memory
      else:
          loss_terms = [
              x[f"{prefix}_loss"] for x in self.test_step_outputs
          ]
          (
              generated_answers,
              unique_ids,
              per_sample_perplexity,
          ) = QAMetrics.convert_dict_outputs_to_lists(
              self.test_step_outputs,
              [
                  "generated_answers",
                  "unique_ids",
                  "per_sample_perplexity",
              ],
          )
          self.test_step_outputs.clear()  # free memory
  
      avg_loss = torch.stack(loss_terms).mean()
  
      eval_dataset = (
          self._test_dl.dataset
          if self.trainer.testing
          else self._validation_dl.dataset
      )
      eval_results, _, _ = self.evaluate(
          eval_dataset.features,
          eval_dataset.examples,
          unique_ids,
          per_sample_perplexity,
          generated_answers,
      )
  
      self.log(f"{prefix}_loss", avg_loss)
      for eval_key in eval_results:
          logging.info(f"{prefix} {eval_key}: {eval_results[eval_key]}")
          self.log(f"{prefix}_{eval_key}", eval_results[eval_key])
  
imports: import collections
  from typing import List, Optional
  import torch
  from omegaconf import DictConfig
  from pytorch_lightning import Trainer
  from transformers import AutoModelForCausalLM
  from nemo.collections.nlp.data.question_answering.data_processor.qa_processing import QAProcessor
  from nemo.collections.nlp.data.question_answering.dataset.qa_gpt_dataset import GPTQADataset
  from nemo.collections.nlp.metrics.qa_metrics import QAMetrics
  from nemo.collections.nlp.models.language_modeling.megatron_gpt_model import MegatronGPTModel
  from nemo.collections.nlp.models.question_answering.qa_base_model import BaseQAModel
  from nemo.core.classes.common import PretrainedModelInfo, typecheck
  from nemo.utils import logging
label_desc: Use image node_id 5 for calling the GPTQAModel obj's underlying member method code with example usage: obj.on_validation_epoch_end() without return types