code: def main(cfg):
      OmegaConf.set_struct(
          cfg, False
      )  # This allows getattr and hasattr methods to function correctly
      log.info(cfg.pretty())
      workdir = os.path.join(BASE_DIR, cfg.model_name)
      if not os.path.exists(workdir):
          os.makedirs(workdir)
  
      cfg.checkpoint_dir = workdir
      cfg.tracker_options.full_res = True
      local_models = {}
      for fold, url in MODELS_URL[cfg.model_name].items():
          local_file = os.path.join(
              workdir, "{}_{}.pt".format(cfg.model_name, fold)
          )
          local_models[fold] = local_file
          download_file(url, local_file)
  
      conf_paths = []
      for fold, model_name in local_models.items():
          cfg.model_name = model_name.replace(".pt", "")
          cfg.tracker_options.full_res = True
          trainer = Trainer(cfg)
          assert str(trainer._checkpoint.data_config.fold) == fold
          trainer.eval(stage_name="test")
  
          conf_path = os.path.join(
              workdir, "{}.npy".format(cfg.model_name)
          )
          np.save(
              conf_path,
              trainer._tracker.full_confusion_matrix.get_confusion_matrix(),
          )
          del trainer
          conf_paths.append(conf_path)
  
      confusion_matrix = ConfusionMatrix.create_from_matrix(
          np.sum([np.load(p) for p in conf_paths], axis=0)
      )
      log_confusion_matrix(confusion_matrix)
  
file_path: torch-points3d/scripts/cv_s3dis.py
imports: import os
  import hydra
  from omegaconf import OmegaConf
  import urllib.request
  import logging
  from torch_points3d.metrics.confusion_matrix import ConfusionMatrix
  import numpy
  from torch_points3d.trainer import Trainer
label_desc: Use image node_id 3 for calling a global function with example usage: main(cfg) without return types