docstr: :param data: data could be a tuple with numpy ndarray with form (x, y) or
         a PyTorch DataLoader or a data creator which takes a config dict and returns a
         torch.utils.data.DataLoader. torch.Tensor should be generated from the
         dataloader.
  :param validation_data: validation data could be a tuple with numpy ndarray
         with form (x, y), a PyTorch DataLoader or a data creator which takes
         a config dict and returns a torch.utils.data.DataLoader. torch.Tensor
         should be generated from the dataloader.
  fit_eval will build a model at the first time it is built
  config will be updated for the second or later times with only non-model-arch
  params be functional
  TODO: check the updated params and decide if the model is needed to be rebuilt
code: def fit_eval(
      self,
      data,
      validation_data=None,
      mc=False,
      verbose=0,
      epochs=1,
      metric=None,
      metric_func=None,
      resources_per_trial=None,
      **config,
  ):
      """
      :param data: data could be a tuple with numpy ndarray with form (x, y) or
             a PyTorch DataLoader or a data creator which takes a config dict and returns a
             torch.utils.data.DataLoader. torch.Tensor should be generated from the
             dataloader.
      :param validation_data: validation data could be a tuple with numpy ndarray
             with form (x, y), a PyTorch DataLoader or a data creator which takes
             a config dict and returns a torch.utils.data.DataLoader. torch.Tensor
             should be generated from the dataloader.
      fit_eval will build a model at the first time it is built
      config will be updated for the second or later times with only non-model-arch
      params be functional
      TODO: check the updated params and decide if the model is needed to be rebuilt
      """
      # todo: support input validation data None
      invalidInputError(
          validation_data is not None, "You must input validation data!"
      )
  
      if not metric:
          invalidInputError(
              False, "You must input a valid metric value for fit_eval."
          )
  
      # resources_per_trial
      if resources_per_trial is not None:
          torch.set_num_threads(resources_per_trial["cpu"])
          os.environ["OMP_NUM_THREADS"] = str(
              resources_per_trial["cpu"]
          )
  
      # update config settings
      def update_config():
          if not isinstance(
              data, types.FunctionType
          ) and not isinstance(data, DataLoader):
              x = self._reshape_input(data[0])
              y = self._reshape_input(data[1])
              config.setdefault("past_seq_len", x.shape[-2])
              config.setdefault("future_seq_len", y.shape[-2])
              config.setdefault("input_feature_num", x.shape[-1])
              config.setdefault("output_feature_num", y.shape[-1])
  
      if not self.model_built:
          update_config()
          self.build(config)
      else:
          tmp_config = copy.copy(self.config)
          tmp_config.update(config)
          self._check_config(**tmp_config)
          self.config.update(config)
  
      # get train_loader and validation_loader
      if isinstance(data, types.FunctionType):
          train_loader = data(self.config)
          validation_loader = validation_data(self.config)
      elif isinstance(data, DataLoader):
          train_loader = data
          invalidInputError(
              isinstance(validation_data, DataLoader),
              "expect validation_data be DataLoader",
          )
          validation_loader = validation_data
      else:
          invalidInputError(
              isinstance(data, tuple)
              and isinstance(validation_data, tuple),
              f"data/validation_data should be a tuple or data creator"
              f" function but found {type(data)}",
          )
          invalidInputError(
              isinstance(data[0], np.ndarray)
              and isinstance(validation_data[0], np.ndarray),
              f"Data and validation_data should be a tuple of np.ndarray "
              f"but found {type(data[0])} as the first element of data.",
          )
          invalidInputError(
              isinstance(data[1], np.ndarray)
              and isinstance(validation_data[1], np.ndarray),
              f"Data and validation_data should be a tuple of np.ndarray "
              f"but found {type(data[1])} as the second element of data.",
          )
          train_data_creator = self._np_to_creator(data)
          valid_data_creator = self._np_to_creator(validation_data)
          train_loader = train_data_creator(self.config)
          validation_loader = valid_data_creator(self.config)
  
      epoch_losses = []
      for i in range(epochs):
          train_loss = self._train_epoch(train_loader)
          epoch_losses.append(train_loss)
      train_stats = {
          "loss": np.mean(epoch_losses),
          "last_loss": epoch_losses[-1],
      }
      val_stats = self._validate(
          validation_loader, metric_name=metric, metric_func=metric_func
      )
      self.onnx_model_built = False
      return val_stats
  
imports: import torch
  from torch.utils.data import TensorDataset, DataLoader
  import types
  import numpy
  import math
  import pandas
  import tempfile
  import os
  import copy
  from bigdl.orca.automl.model.abstract import BaseModel, ModelBuilder
  from bigdl.orca.automl.metrics import Evaluator
  from bigdl.orca.automl.pytorch_utils import LR_NAME, DEFAULT_LR
  from bigdl.dllib.utils.log4Error import *
label_desc: Use image node_id 7 for calling the PytorchBaseModel obj's underlying member method code with example usage: obj.fit_eval(data, validation_data, mc, verbose, epochs, metric, metric_func, resources_per_trial) and returns: val_stats