class_docstr: Callable for pruning archives in the optimizer class.
  See Optimizer.pruning attribute, called at each "tell".
  
  Parameters
  ----------
  min_len: int
      minimum length of the pruned archive.
  max_len: int
      length at which pruning is activated (maximum allowed length for the archive).
  
  Note
  ----
  For each of the 3 criteria (optimistic, pessimistic and average), the min_len best (lowest)
  points will be kept, which can lead to at most 3 * min_len points.
code: def _prune(self, archive: Archive[MultiValue]) -> Archive[MultiValue]:
      self._num_prunings += 1
      # separate function to ease profiling
      quantiles: tp.Dict[str, float] = {}
      threshold = float(self.min_len + 1) / len(archive)
      names = ["optimistic", "pessimistic", "average"]
      for name in names:
          quantiles[name] = np.quantile(  # type: ignore
              [v.get_estimation(name) for v in archive.values()],
              threshold,
              method="lower",
          )
      new_archive: Archive[MultiValue] = Archive()
      new_archive.bytesdict = {
          b: v
          for b, v in archive.bytesdict.items()
          if any(v.get_estimation(n) < quantiles[n] for n in names)
      }  # strict comparison to make sure we prune even for values repeated maaany times
      # this may remove all points though, but nevermind for now
      return new_archive
  
imports: import math
  import operator
  import numpy
  from nevergrad.parametrization import parameter
  from nevergrad.parametrization.utils import float_penalty
  import nevergrad.common.typing
  from nevergrad.common.tools import OrderedSet
label_desc: Use image node_id 3 for calling the Pruning obj's underlying member method code with example usage: obj._prune(archive) and returns: new_archive