docs: public OutlierResult run(Database database, Relation<NumberVector> relation) {
      final int dbdim = RelationUtil.dimensionality(relation);
      final int mindim = dbdim >> 1;
      final int maxdim = dbdim - 1;
      final Random rand = rnd.getSingleThreadedRandom();
  
      ArrayList<OutlierResult> results = new ArrayList<>(num);
      {
        FiniteProgress prog = LOG.isVerbose() ? new FiniteProgress("LOF iterations", num, LOG) : null;
        for(int i = 0; i < num; i++) {
          long[] dimset = randomSubspace(dbdim, mindim, maxdim, rand);
          SubspaceEuclideanDistanceFunction df = new SubspaceEuclideanDistanceFunction(dimset);
          LOF<NumberVector> lof = new LOF<>(k, df);
  
          // run LOF and collect the result
          OutlierResult result = lof.run(database, relation);
          results.add(result);
          LOG.incrementProcessed(prog);
        }
        LOG.ensureCompleted(prog);
      }
  
      WritableDoubleDataStore scores = DataStoreUtil.makeDoubleStorage(relation.getDBIDs(), DataStoreFactory.HINT_STATIC);
      DoubleMinMax minmax = new DoubleMinMax();
      if(breadth) {
        FiniteProgress cprog = LOG.isVerbose() ? new FiniteProgress("Combining results", relation.size(), LOG) : null;
        @SuppressWarnings("unchecked")
        Pair<DBIDIter, DoubleRelation>[] IDVectorOntoScoreVector = (Pair<DBIDIter, DoubleRelation>[]) new Pair[results.size()];
  
        // Mapping score-sorted DBID-Iterators onto their corresponding scores.
        // We need to initialize them now be able to iterate them "in parallel".
        {
          int i = 0;
          for(OutlierResult r : results) {
            IDVectorOntoScoreVector[i] = new Pair<DBIDIter, DoubleRelation>(r.getOrdering().order(relation.getDBIDs()).iter(), r.getScores());
            i++;
          }
        }
  
        // Iterating over the *lines* of the AS_t(i)-matrix.
        for(int i = 0; i < relation.size(); i++) {
          // Iterating over the elements of a line (breadth-first).
          for(Pair<DBIDIter, DoubleRelation> pair : IDVectorOntoScoreVector) {
            DBIDIter iter = pair.first;
            // Always true if every algorithm returns a complete result (one score
            // for every DBID).
            if(iter.valid()) {
              double score = pair.second.doubleValue(iter);
              if(Double.isNaN(scores.doubleValue(iter))) {
                scores.putDouble(iter, score);
                minmax.put(score);
              }
              iter.advance();
            }
            else {
              LOG.warning("Incomplete result: Iterator does not contain |DB| DBIDs");
            }
          }
          // Progress does not take the initial mapping into account.
          LOG.incrementProcessed(cprog);
        }
        LOG.ensureCompleted(cprog);
      }
      else {
        FiniteProgress cprog = LOG.isVerbose() ? new FiniteProgress("Combining results", relation.size(), LOG) : null;
        for(DBIDIter iter = relation.iterDBIDs(); iter.valid(); iter.advance()) {
          double sum = 0.0;
          for(OutlierResult r : results) {
            final double s = r.getScores().doubleValue(iter);
            if(!Double.isNaN(s)) {
              sum += s;
            }
          }
          scores.putDouble(iter, sum);
          minmax.put(sum);
          LOG.incrementProcessed(cprog);
        }
        LOG.ensureCompleted(cprog);
      }
      OutlierScoreMeta meta = new BasicOutlierScoreMeta(minmax.getMin(), minmax.getMax());
      DoubleRelation scoreres = new MaterializedDoubleRelation("Feature bagging", "fb-outlier", scores, relation.getDBIDs());
      return new OutlierResult(meta, scoreres);
    }