private protected static FeatureSubsetModel <TOutput>[] CreateModels <T>(List <FeatureSubsetModel <TOutput> > models) where T : IPredictorProducing <TOutput> { var subsetModels = new FeatureSubsetModel <TOutput> [models.Count]; for (int i = 0; i < models.Count; i++) { subsetModels[i] = new FeatureSubsetModel <TOutput>( (T)models[i].Predictor, models[i].SelectedFeatures, models[i].Metrics); } return(subsetModels); }
public int Compare(FeatureSubsetModel <TOutput> x, FeatureSubsetModel <TOutput> y) { if (x == null || y == null) { return((x == null ? 0 : 1) - (y == null ? 0 : 1)); } double xValue = 0; var found = false; foreach (var kvp in x.Metrics) { if (_metricName == kvp.Key) { xValue = kvp.Value; found = true; break; } } if (!found) { throw Contracts.Except("Metrics did not contain the requested metric '{0}'", _metricName); } double yValue = 0; found = false; foreach (var kvp in y.Metrics) { if (_metricName == kvp.Key) { yValue = kvp.Value; found = true; break; } } if (!found) { throw Contracts.Except("Metrics did not contain the requested metric '{0}'", _metricName); } if (xValue > yValue) { return(_isAscMetric ? -1 : 1); } if (yValue > xValue) { return(_isAscMetric ? 1 : -1); } return(0); }
private TPredictor TrainCore(IChannel ch, RoleMappedData data) { Host.AssertValue(ch); ch.AssertValue(data); // 1. Subset Selection var stackingTrainer = Combiner as IStackingTrainer <TOutput>; //REVIEW: Implement stacking for Batch mode. ch.CheckUserArg(stackingTrainer == null || Args.BatchSize <= 0, nameof(Args.BatchSize), "Stacking works only with Non-batch mode"); var validationDataSetProportion = SubModelSelector.ValidationDatasetProportion; if (stackingTrainer != null) { validationDataSetProportion = Math.Max(validationDataSetProportion, stackingTrainer.ValidationDatasetProportion); } var needMetrics = Args.ShowMetrics || Combiner is IWeightedAverager; var models = new List <FeatureSubsetModel <TOutput> >(); _subsetSelector.Initialize(data, NumModels, Args.BatchSize, validationDataSetProportion); int batchNumber = 1; foreach (var batch in _subsetSelector.GetBatches(Host.Rand)) { // 2. Core train ch.Info("Training {0} learners for the batch {1}", Trainers.Length, batchNumber++); var batchModels = new FeatureSubsetModel <TOutput> [Trainers.Length]; Parallel.ForEach(_subsetSelector.GetSubsets(batch, Host.Rand), new ParallelOptions() { MaxDegreeOfParallelism = Args.TrainParallel ? -1 : 1 }, (subset, state, index) => { ch.Info("Beginning training model {0} of {1}", index + 1, Trainers.Length); Stopwatch sw = Stopwatch.StartNew(); try { if (EnsureMinimumFeaturesSelected(subset)) { var model = new FeatureSubsetModel <TOutput>( Trainers[(int)index].Train(subset.Data), subset.SelectedFeatures, null); SubModelSelector.CalculateMetrics(model, _subsetSelector, subset, batch, needMetrics); batchModels[(int)index] = model; } } catch (Exception ex) { ch.Assert(batchModels[(int)index] == null); ch.Warning(ex.Sensitivity(), "Trainer {0} of {1} was not learned properly due to the exception '{2}' and will not be added to models.", index + 1, Trainers.Length, ex.Message); } ch.Info("Trainer {0} of {1} finished in {2}", index + 1, Trainers.Length, sw.Elapsed); }); var modelsList = batchModels.Where(m => m != null).ToList(); if (Args.ShowMetrics) { PrintMetrics(ch, modelsList); } modelsList = SubModelSelector.Prune(modelsList).ToList(); if (stackingTrainer != null) { stackingTrainer.Train(modelsList, _subsetSelector.GetTestData(null, batch), Host); } models.AddRange(modelsList); int modelSize = Utils.Size(models); if (modelSize < Utils.Size(Trainers)) { ch.Warning("{0} of {1} trainings failed.", Utils.Size(Trainers) - modelSize, Utils.Size(Trainers)); } ch.Check(modelSize > 0, "Ensemble training resulted in no valid models."); } return(CreatePredictor(models)); }
public override void CalculateMetrics(FeatureSubsetModel <TOutput> model, ISubsetSelector subsetSelector, Subset subset, Batch batch, bool needMetrics) { base.CalculateMetrics(model, subsetSelector, subset, batch, true); }