docstr: Fast version of Rich Caruana's ensemble selection method.
docstr_tok: ["Fast","version","of","Rich","Caruana","'s","ensemble","selection","method","."]
code: def _fast(
      self,
      predictions: List[np.ndarray],
      labels: np.ndarray,
      *,
      X_data: SUPPORTED_FEAT_TYPES | None = None,
  ) -> None:
      """Fast version of Rich Caruana's ensemble selection method."""
      self.num_input_models_ = len(predictions)
      rand = check_random_state(self.random_state)
  
      ensemble = []  # type: List[np.ndarray]
      trajectory = []
      order = []
  
      ensemble_size = self.ensemble_size
  
      weighted_ensemble_prediction = np.zeros(
          predictions[0].shape,
          dtype=np.float64,
      )
      fant_ensemble_prediction = np.zeros(
          weighted_ensemble_prediction.shape,
          dtype=np.float64,
      )
      for i in range(ensemble_size):
          losses = np.zeros(
              (len(predictions)),
              dtype=np.float64,
          )
          s = len(ensemble)
          if s > 0:
              np.add(
                  weighted_ensemble_prediction,
                  ensemble[-1],
                  out=weighted_ensemble_prediction,
              )
  
          # Memory-efficient averaging!
          for j, pred in enumerate(predictions):
              # fant_ensemble_prediction is the prediction of the current ensemble
              # and should be
              #
              #   ([predictions[selected_prev_iterations] + predictions[j])/(s+1)
              #
              # We overwrite the contents of fant_ensemble_prediction directly with
              # weighted_ensemble_prediction + new_prediction and then scale for avg
              np.add(
                  weighted_ensemble_prediction,
                  pred,
                  out=fant_ensemble_prediction,
              )
              np.multiply(
                  fant_ensemble_prediction,
                  (1.0 / float(s + 1)),
                  out=fant_ensemble_prediction,
              )
  
              losses[j] = calculate_losses(
                  solution=labels,
                  prediction=fant_ensemble_prediction,
                  task_type=self.task_type,
                  metrics=[self.metric],
                  X_data=X_data,
                  scoring_functions=None,
              )[self.metric.name]
  
          all_best = np.argwhere(losses == np.nanmin(losses)).flatten()
  
          best = rand.choice(all_best)
  
          ensemble.append(predictions[best])
          trajectory.append(losses[best])
          order.append(best)
  
          # Handle special case
          if len(predictions) == 1:
              break
  
      self.indices_ = order
      self.trajectory_ = trajectory
      self.train_loss_ = trajectory[-1]
  
imports: from __future__ import annotations
  from typing import Dict, List, Sequence, Tuple, Union
  import random
  import warnings
  from collections import Counter
  import numpy
  from sklearn.utils import check_random_state
  from autosklearn.automl_common.common.utils.backend import Backend
  from autosklearn.constants import TASK_TYPES
  from autosklearn.data.validation import SUPPORTED_FEAT_TYPES
  from autosklearn.ensemble_building.run import Run
  from autosklearn.ensembles.abstract_ensemble import AbstractEnsemble
  from autosklearn.metrics import Scorer, calculate_losses
  from autosklearn.pipeline.base import BasePipeline
label_desc: Use image node_id 4 for calling the EnsembleSelection obj's underlying member method code with example usage: obj._fast(predictions, labels) without return types