class_docstr: Used to pre-train the actor model to generate better prompts.
  
  Args:
      config (ConfigActor): Configuration for the actor model
  
  Attributes:
      config (ConfigActor): Configuration for the actor model
      model (ActorModel): Actor model
      loss_function (torch.nn.CrossEntropyLoss): Loss function
      optimizer (torch.optim.Adam): Optimizer
      validation_flag (bool): Flag to indicate if the validation dataset
          is provided
      train_dataset (ActorDataset): Training dataset
      train_dataloader (DataLoader): Training dataloader
      validation_dataset (ActorDataset): Validation dataset
      validation_dataloader (DataLoader): Validation dataloader
      scheduler (torch.optim.lr_scheduler): Learning rate scheduler
      training_stats (TrainingStats): Training statistics
      model_engine (ModelEngine): Model engine for deepspeed training
      accelerator (Accelerator): Accelerator for accelerate training
  
  Methods:
      train: Train the actor model
      load_checkpoint: Load a checkpoint
      save_checkpoint: Save a checkpoint
code: def __init__(self, config: ConfigActor) -> None:
      # store config
      self.config = config
  
      # load the model
      self.actor = ActorModel(config)
  
      # define loss function
      self.loss_function = torch.nn.CrossEntropyLoss()
  
      # define optimizer
      self.optimizer = torch.optim.AdamW(
          self.actor.parameters(), lr=config.lr, weight_decay=1e-5
      )
  
      # check if validation dataset is provided
      self.validation_flag = False
      if config.validation_dataset_path is not None:
          self.validation_flag = True
  
      # create dataset and dataloaders
      self.train_dataset = ActorDataset(config.train_dataset_path)
      self.train_dataloader = DataLoader(
          self.train_dataset, batch_size=config.batch_size
      )
      if self.validation_flag:
          self.eval_dataset = ActorDataset(
              config.validation_dataset_path
          )
          self.validation_dataloader = DataLoader(
              self.eval_dataset, batch_size=config.batch_size
          )
  
      # define scheduler for the learning rate
      # learning rate is decreased until 10% of the initial value
      self.scheduler = (
          torch.optim.lr_scheduler.CosineAnnealingWarmRestarts(
              self.optimizer,
              T_0=len(self.train_dataset) // config.batch_size,
              T_mult=1,
              eta_min=config.lr * 0.1,
          )
      )
  
      # define training statistics
      stat_path = ModelLoader.get_training_stats_path(config)
      self.training_stats = TrainingStats(stat_path)
  
      # consistency check between accelerate and deepspeed
      if config.accelerate_enable and config.deepspeed_enable:
          raise ValueError(
              "Both DeepSpeed and Accelerate are enabled for the Actor."
              "Please choose one of them."
          )
  
      # initialize deepspeed
      self.model_engine = None
      if config.deepspeed_enable is True:
          if config.deepspeed_config_path is None:
              raise ValueError(
                  "DeepSpeed config path is None, but deepspeed is enabled"
              )
          if os.path.exists(config.deepspeed_config_path) is False:
              raise ValueError(
                  f"DeepSpeed config path {config.deepspeed_config_path}"
                  f"does not exist"
              )
          (
              self.model_engine,
              self.optimizer,
              self.train_dataloader,
              _,
          ) = deepspeed.initialize(
              args=None,
              model=self.actor,
              model_parameters=self.actor.parameters(),
              training_data=self.train_dataset,
              config=self.config.deepspeed_config_path,
          )
          print("Training with DeepSpeed")
  
      # initialize accelerate
      self.accelerator = None
      if config.accelerate_enable is True:
          self.accelerator = Accelerator()
          (
              self.actor,
              self.optimizer,
              self.train_dataloader,
              self.scheduler,
          ) = self.accelerator.prepare(
              self.actor,
              self.optimizer,
              self.train_dataloader,
              self.scheduler,
          )
          print("Training with Accelerate")
  
imports: import json
  import yaml
  import os
  import shutil
  import deepspeed
  import torch
  from accelerate import Accelerator
  from beartype import beartype
  from beartype.typing import Tuple
  from einops import rearrange
  from peft import get_peft_model, LoraConfig, TaskType
  from torch.utils.data import DataLoader, Dataset
  from transformers import AutoModelForCausalLM, AutoTokenizer
  from chatllama.rlhf.config import ConfigActor
  from chatllama.rlhf.model_list import hf_models_causal_lm, llama_models, hf_models
  from chatllama.rlhf.model_loader import ModelLoader
  from chatllama.rlhf.utils import TrainingStats
label_desc: Use image node_id 1 to create a new ActorTrainer object  with example: obj = ActorTrainer(config)