Beispiel #1
0
        public void SetObservedVariables(double[][][] featureValues, GaussianArray priorWeightMeans, GammaArray priorWeightPrecisions, bool[][] labels = null)
        {
#if !USE_PRECOMPILED_ALGORITHM
            numberOfResidents.ObservedValue = featureValues.Length;
            numberOfExamples.ObservedValue  = featureValues.Select(ia => ia.Length).ToArray();
            numberOfFeatures.ObservedValue  = featureValues[0][0].Length;
            noisePrecision.ObservedValue    = 1;

            if (labels != null)
            {
                activities.ObservedValue = labels;
            }

            this.featureValues.ObservedValue = featureValues;

            weightPriorMeans.ObservedValue      = DistributionArrayHelpers.Copy(priorWeightMeans);
            weightPriorPrecisions.ObservedValue = DistributionArrayHelpers.Copy(priorWeightPrecisions);
#else
            algorithm.SetObservedValue(numberOfResidents.Name, featureValues.Length);
            algorithm.SetObservedValue(numberOfExamples.Name, featureValues[0].Length);
            algorithm.SetObservedValue(numberOfFeatures.Name, featureValues[0][0].Length);
            algorithm.SetObservedValue(noisePrecision.Name, 1.0);
            algorithm.SetObservedValue(this.featureValues.Name, featureValues);
            algorithm.SetObservedValue(weightPriorMeans.Name, DistributionArrayHelpers.Copy(priorWeightMeans));
            algorithm.SetObservedValue(weightPriorPrecisions.Name, DistributionArrayHelpers.Copy(priorWeightPrecisions));

            if (labels != null)
            {
                algorithm.SetObservedValue(activities.Name, labels);
            }
#endif
        }
        /// <summary>
        /// Sets the observed values.
        /// </summary>
        /// <param name="instances">The instances.</param>
        /// <param name="featureSet">The feature buckets.</param>
        /// <param name="mode">The mode.</param>
        /// <param name="priors">The priors.</param>
        /// <exception cref="System.InvalidOperationException">Data is null</exception>
        /// <exception cref="System.ArgumentNullException">parameters;@Mode expected in parameters</exception>
        /// <exception cref="System.ArgumentException"></exception>
        public override void SetObservedValues(IList <Inputs.Instance> instances, FeatureSet featureSet, InputMode mode, Priors priors)
        {
            if (instances == null)
            {
                throw new InvalidOperationException("Data is null");
            }

            this.NumberOfMessages.ObservedValue = instances.Count;
            this.NumberOfFeatures.ObservedValue = featureSet.FeatureVectorLength;

            this.NoiseVariance.ObservedValue = priors.NoiseVariance;

            if (mode == InputMode.Training)
            {
                this.RepliedTo.ObservedValue    = instances.Select(ia => ia.Label).ToArray();
                this.WeightPriors.ObservedValue = DistributionArrayHelpers.DistributionArray(priors.Weights.Values);
            }
            else
            {
                // This is testing, don't set isRepliedTo observed values
                this.WeightPriors.ObservedValue = DistributionArrayHelpers.Copy(priors.Weights.Values);
            }

            var featureIndices = featureSet.FeatureBuckets.Select((ia, i) => new { ia, i }).ToDictionary(anon => anon.ia, anon => anon.i);

            this.FeatureIndices.ObservedValue =
                instances.Select(ia => ia.FeatureValues.Select(fbv => featureIndices[fbv.Key]).ToArray()).ToArray();

            this.FeatureValue.ObservedValue  = instances.Select(ia => ia.FeatureValues.Select(fbv => fbv.Value).ToArray()).ToArray();
            this.FeatureCounts.ObservedValue = this.FeatureIndices.ObservedValue.Select(ia => ia.Length).ToArray();
        }
        public void Test(int numberOfActivities, double[][][] featureValues, Gaussian[] priorWeightMeans, Gamma[] priorWeightPrecisions, out Discrete[][] posteriorActivities)
        {
            SetObservedVariables(numberOfActivities, featureValues);

            weightPriorMeans.ObservedValue      = DistributionArrayHelpers.Copy(priorWeightMeans);
            weightPriorPrecisions.ObservedValue = DistributionArrayHelpers.Copy(priorWeightPrecisions);


            posteriorActivities = engine.Infer <Discrete[][]>(activities);
        }
Beispiel #4
0
        public Bernoulli ComputeEvidence(DataSet dataSet, Marginals priors)
        {
            SetObservedVariables(
                dataSet.Features,
                DistributionArrayHelpers.Copy(priors.WeightMeans),
                DistributionArrayHelpers.Copy(priors.WeightPrecisions),
                dataSet.Labels);

            engine.Algorithm.DefaultNumberOfIterations = 1;

            return(engine.Infer <Bernoulli>(evidence));
        }
Beispiel #5
0
        /// <summary>
        /// Test the specified dataSet and priors.
        /// </summary>
        /// <param name="dataSet">Data set.</param>
        /// <param name="priors">Priors.</param>
        public Bernoulli[][] Test(DataSet dataSet, Marginals priors)
        {
            SetObservedVariables(
                dataSet.Features,
                DistributionArrayHelpers.Copy(priors.WeightMeans),
                DistributionArrayHelpers.Copy(priors.WeightPrecisions));

#if !USE_PRECOMPILED_ALGORITHM
            var posteriorActivities = engine.Infer <Bernoulli[][]>(activities);
#else
            algorithm.Execute(1);
            var posteriorActivities = algorithm.Marginal <Bernoulli[][]>(activities.Name);
#endif

            return(posteriorActivities);
        }
Beispiel #6
0
        /// <summary>
        /// Sets the observed values.
        /// </summary>
        /// <param name="instances">The instances.</param>
        /// <param name="featureSet">The feature set.</param>
        /// <param name="mode">The mode.</param>
        /// <param name="priors">The priors.</param>
        /// <exception cref="System.InvalidOperationException">Data is null</exception>
        public override void SetObservedValues(IList <Inputs.Instance> instances, FeatureSet featureSet, InputMode mode, Priors priors)
        {
            if (instances == null)
            {
                throw new InvalidOperationException("Data is null");
            }

            this.NumberOfMessages.ObservedValue = instances.Count;
            this.NumberOfFeatures.ObservedValue = featureSet.FeatureVectorLength;

            this.NoiseVariance.ObservedValue = priors.NoiseVariance;

            if (mode == InputMode.Training)
            {
                this.RepliedTo.ObservedValue      = instances.Select(ia => ia.Label).ToArray();
                this.WeightPriors.ObservedValue   = DistributionArrayHelpers.DistributionArray(priors.Weights.Values);
                this.ThresholdPrior.ObservedValue = priors.Threshold;
            }
            else
            {
                // This is testing, don't set isRepliedTo observed values
                this.RepliedTo.ClearObservedValue();
                this.WeightPriors.ObservedValue   = DistributionArrayHelpers.Copy(priors.Weights.Values);
                this.ThresholdPrior.ObservedValue = priors.Threshold;
            }

            // Convert feature values to dense jagged array
            var featureValues = new double[instances.Count][];

            for (int i = 0; i < instances.Count; i++)
            {
                featureValues[i] = new double[featureSet.FeatureVectorLength];
                foreach (var featureBucketValue in instances[i].FeatureValues)
                {
                    int index = instances[i].FeatureSet.FeatureBuckets.IndexOf(featureBucketValue.Key);
                    if (index < 0)
                    {
                        throw new InvalidOperationException("Bucket index not found");
                    }

                    featureValues[i][index] = featureBucketValue.Value;
                }
            }

            this.FeatureValue.ObservedValue = featureValues;
        }
Beispiel #7
0
        /// <summary>
        /// Sets the observed values.
        /// </summary>
        /// <param name="instances">The instances.</param>
        /// <param name="featureSet">The feature set.</param>
        /// <param name="mode">The mode.</param>
        /// <param name="communityPriors">The community priors.</param>
        /// <exception cref="System.InvalidOperationException">Data is null</exception>
        public override void SetObservedValues(IList <IList <Inputs.Instance> > instances, FeatureSet featureSet, InputMode mode, CommunityPriors communityPriors)
        {
            // This is for personalisation training and testing
            if (instances == null)
            {
                throw new InvalidOperationException("Data is null");
            }

            this.NumberOfPeople.ObservedValue   = instances.Count;
            this.NumberOfMessages.ObservedValue = instances.Select(ia => ia.Count).ToArray();

            this.NumberOfFeatures.ObservedValue = mode == InputMode.CommunityTraining
                                                      ? featureSet.SharedFeatureVectorLength
                                                      : featureSet.FeatureVectorLength;

            this.NoiseVariance.ObservedValue = communityPriors.NoiseVariance;

            if (mode == InputMode.CommunityTraining || mode == InputMode.Training)
            {
                this.RepliedTo.ObservedValue = instances.Select(inner => inner.Select(ia => ia.Label).ToArray()).ToArray();
            }

            this.WeightMeanPriors.ObservedValue      = DistributionArrayHelpers.Copy(communityPriors.WeightMeans.Values);
            this.WeightPrecisionPriors.ObservedValue = DistributionArrayHelpers.Copy(communityPriors.WeightPrecisions.Values);

            // If this is community training, we only want shared features
            Func <KeyValuePair <FeatureBucket, double>, bool> predicate =
                fbv => mode != InputMode.CommunityTraining || fbv.Key.Feature.IsShared;

            this.FeatureIndices.ObservedValue =
                instances.Select(
                    inner =>
                    inner.Select(
                        ia => ia.FeatureValues.Where(predicate).Select(fbv => featureSet.FeatureBuckets.IndexOf(fbv.Key)).ToArray())
                    .ToArray()).ToArray();

            this.FeatureValue.ObservedValue =
                instances.Select(
                    inner => inner.Select(ia => ia.FeatureValues.Where(predicate).Select(fbv => fbv.Value).ToArray()).ToArray()).ToArray();

            this.FeatureCounts.ObservedValue =
                this.FeatureValue.ObservedValue.Select(inner => inner.Select(ia => ia.Length).ToArray()).ToArray();
        }
        public void Train(int numberOfActivities, double[][][] featureValues, int[][] labels,
                          out Gaussian[][][] posteriorWeights, out Gaussian[] posteriorWeightMeans, out Gamma[] posteriorWeightPrecisions)
        {
            SetObservedVariables(numberOfActivities, featureValues);

            activities.ObservedValue = labels;

            var priorWeightMeans      = new Gaussian[numberOfActivities];
            var priorWeightPrecisions = new Gamma[numberOfActivities];

            for (int i = 0; i < numberOfActivities; i++)
            {
                priorWeightMeans[i]      = new Gaussian(0, 1);
                priorWeightPrecisions[i] = new Gamma(4, 0.5);
            }

            weightPriorMeans.ObservedValue      = DistributionArrayHelpers.Copy(priorWeightMeans);
            weightPriorPrecisions.ObservedValue = DistributionArrayHelpers.Copy(priorWeightPrecisions);

            posteriorWeights          = engine.Infer <Gaussian[][][]>(weights);
            posteriorWeightMeans      = engine.Infer <Gaussian[]>(weightMeans);
            posteriorWeightPrecisions = engine.Infer <Gamma[]>(weightPrecisions);
        }
Beispiel #9
0
        /// <summary>
        /// Train the specified dataSet and priors for the specified number of iterations.
        /// </summary>
        /// <param name="dataSet">Data set.</param>
        /// <param name="priors">Priors.</param>
        /// <param name="numberOfIterations">Number of iterations.</param>
        public Marginals Train(DataSet dataSet, Marginals priors, int numberOfIterations = 10)
        {
            SetObservedVariables(
                dataSet.Features,
                DistributionArrayHelpers.Copy(priors.WeightMeans),
                DistributionArrayHelpers.Copy(priors.WeightPrecisions),
                dataSet.Labels);

#if !USE_PRECOMPILED_ALGORITHM
            engine.Algorithm.DefaultNumberOfIterations = numberOfIterations;
            var posteriorWeights          = engine.Infer <Gaussian[][]>(weights);
            var posteriorWeightMeans      = engine.Infer <Gaussian[]>(weightMeans);
            var posteriorWeightPrecisions = engine.Infer <Gamma[]>(weightPrecisions);
#else
            algorithm.Execute(numberOfIterations);
            var posteriorWeights          = algorithm.Marginal <Gaussian[][]>(weights.Name);
            var posteriorWeightMeans      = algorithm.Marginal <Gaussian[]>(weightMeans.Name);
            var posteriorWeightPrecisions = algorithm.Marginal <Gamma[]>(weightPrecisions.Name);
#endif

            return(new Marginals {
                Weights = posteriorWeights, WeightMeans = posteriorWeightMeans, WeightPrecisions = posteriorWeightPrecisions
            });
        }
Beispiel #10
0
 /// <summary>
 /// Initializes a new instance of the <see cref="Marginals"/> class.
 /// </summary>
 /// <param name="marginals">Marginals.</param>
 public Marginals(Marginals marginals)
 {
     Weights          = marginals.Weights == null ? null : marginals.Weights.Select(ia => DistributionArrayHelpers.Copy(ia).ToArray()).ToArray();
     WeightMeans      = marginals.WeightMeans == null ? null : DistributionArrayHelpers.Copy(marginals.WeightMeans).ToArray();
     WeightPrecisions = marginals.WeightPrecisions == null ? null : DistributionArrayHelpers.Copy(marginals.WeightPrecisions).ToArray();
 }
        /// <summary>
        /// Initializes a new instance of the <see cref="ToyDataRunner"/> class.
        /// </summary>
        /// <param name="trainModel">Train model.</param>
        /// <param name="testModel">Test model.</param>
        public static void Run(BinaryModel trainModel, BinaryModel testModel, bool testTransfer, bool testActive, bool testActiveTransfer)
        {
            var phase1PriorMean      = new Gaussian(4, 1);
            var phase1PriorPrecision = new Gamma(1, 1);
            var phase2PriorMean      = new Gaussian(4, 1);
            var phase2PriorPrecision = new Gamma(1, 1);

            // Generate data for 5 individuals
            var data = new List <ToyData>();

            for (int i = 0; i < 3; i++)
            {
                var toy = new ToyData
                {
                    // NumberOfInstances = 200,
                    // NumberOfHoldoutInstances = i == 0 ? 0 : 1000,
                    NumberOfResidents  = 5,
                    NumberOfFeatures   = NumberOfFeatures,
                    NumberOfActivities = 2,
                    UseBias            = false,
                    TruePriorMean      = i == 0 ? phase1PriorMean : phase2PriorMean,
                    TruePriorPrecision = i == 0 ? phase1PriorPrecision : phase2PriorPrecision
                };

                toy.Generate(i == 2 ? NoisyExampleProportion : 0.0, 200);
                if (i != 0)
                {
                    // no need for holdout data in training set
                    toy.Generate(0.0, 1000, true);
                }

                data.Add(toy);
            }

            var priors = new Marginals
            {
                WeightMeans      = DistributionArrayHelpers.CreateGaussianArray(NumberOfFeatures, 0, 1).ToArray(),
                WeightPrecisions = DistributionArrayHelpers.CreateGammaArray(NumberOfFeatures, 1, 1).ToArray()
            };

            Console.WriteLine("Data Generated");

            // TODO: Create meta-features that allow us to do the first form of transfer learning

            // Train the community model
            Console.WriteLine("Training Community Model");
            var communityExperiment = new Experiment {
                TrainModel = trainModel, TestModel = testModel, Name = "Community"
            };

            communityExperiment.RunBatch(data[0].DataSet, priors);
            // PrintWeightPriors(communityExperiment.Posteriors, trainData.CommunityWeights);

            // Utils.PlotPosteriors(communityExperiment.Posteriors.Weights, data[0].Weights);
            // Utils.PlotPosteriors(communityExperiment.Posteriors.WeightMeans, communityExperiment.Posteriors.WeightPrecisions, null, "Community weights", "Feature");

            // return;

            if (testTransfer)
            {
                // Do online learning
                // Console.WriteLine("Testing Online Model");
                var onlineExperiment = new Experiment {
                    TrainModel = trainModel, TestModel = testModel, Name = "Online"
                };
                onlineExperiment.RunOnline(data[1].DataSet, data[1].HoldoutSet, priors);

                // Do transfer learning
                // Console.WriteLine("Testing Community Model");
                var personalisationExperiment = new Experiment {
                    TrainModel = trainModel, TestModel = testModel, Name = "Community"
                };
                personalisationExperiment.RunOnline(data[1].DataSet, data[1].HoldoutSet, communityExperiment.Posteriors);

                // Plot cumulative metrics
                Utils.PlotCumulativeMetrics(new[] { onlineExperiment, personalisationExperiment }, "Toy Transfer");
            }
            else
            {
                Console.WriteLine("Skipping Transfer Learning");
            }

            // ACTIVE MODEL
            if (testActive)
            {
                ActiveTransfer(trainModel, testModel, data, "Toy Active", priors);
            }
            else
            {
                Console.WriteLine("Skipping Active Learning");
            }

            if (testActiveTransfer)
            {
                Console.WriteLine("Note that the transfer learning is very effective here, so the active learning doesn't add much");
                ActiveTransfer(trainModel, testModel, data, "Toy Active Transfer", communityExperiment.Posteriors);
            }
            else
            {
                Console.WriteLine("Skipping Active Transfer Learning");
            }

            // Now create different costs for acquiring labels - want to demonstrate that we choose from all 3 possible labels
        }
Beispiel #12
0
        /// <summary>
        /// Initializes a new instance of the <see cref="ActiveTransfer.ToyDataRunner"/> class.
        /// </summary>
        /// <param name="trainModel">Train model.</param>
        /// <param name="testModel">Test model.</param>
        public void Run(BinaryModel trainModel, BinaryModel testModel, BinaryModel evidenceModel, bool testVOI, bool testActiveEvidence)
        {
            const int    NumberOfResidents = 7;
            const double KeepProportion    = 1.0;

            var selectedFeatures = new HashSet <int>(Enumerable.Range(0, 48));

            var ted = Source.GetDataSet(Enumerable.Range(1, 14), AddBias, selectedFeatures, KeepProportion);
            var trd = Target.GetDataSet(Enumerable.Range(1, 25), AddBias, selectedFeatures, KeepProportion);
            // var ted = Source.GetDataSet( Enumerable.Range( 1, 1 ), AddBias, selectedFeatures, KeepProportion );
            // var trd = Target.GetDataSet( Enumerable.Range( 1, 20 ), AddBias, selectedFeatures, KeepProportion );
            // var hod = Target.GetDataSet( Enumerable.Range( 1 + NumberOfResidents * 1, NumberOfResidents ) );

            DataSet testSet;
            DataSet holdoutSet;

            ted.SplitTrainTest(0.5, out testSet, out holdoutSet);

            var NumFeatures = trd.Features.First().First().Count();

            var trainData = new ToyData
            {
                NumberOfResidents  = trd.NumberOfResidents,
                NumberOfFeatures   = NumFeatures,
                NumberOfActivities = 2,
                UseBias            = false,
                DataSet            = trd
            };

            var testData = new ToyData
            {
                NumberOfResidents  = NumberOfResidents,
                NumberOfFeatures   = NumFeatures,
                NumberOfActivities = 2,
                UseBias            = false,
                DataSet            = testSet,
                HoldoutSet         = holdoutSet
            };

            var priors = new Marginals
            {
                WeightMeans      = DistributionArrayHelpers.CreateGaussianArray(trainData.NumberOfFeatures, 0.0, 1.0).ToArray(),
                WeightPrecisions = DistributionArrayHelpers.CreateGammaArray(trainData.NumberOfFeatures, 1.0, 1.0).ToArray()
            };

            // TODO: Create meta-features that allow us to do the first form of transfer learning

            // Train the community model
            var communityExperiment = new Experiment
            {
                TrainModel    = trainModel,
                TestModel     = testModel,
                EvidenceModel = evidenceModel,
                Name          = "Community"
            };

            communityExperiment.RunBatch(trainData.DataSet, priors);
            // communityExperiment.Posteriors.WeightPrecisions = priors.WeightPrecisions;

            // if (false)
            // {
            //     Utils.PlotPosteriors(communityExperiment.Posteriors.WeightMeans, communityExperiment.Posteriors.WeightPrecisions, null, "Community weights", "Feature", ShowPlots);
            //     Utils.PlotPosteriors(communityExperiment.Posteriors.WeightMeans, communityExperiment.Posteriors.WeightPrecisions, null, "Community weights (prior precision)", "Feature", ShowPlots);
            // }

            // Print top features
            // var topWeights = communityExperiment.Posteriors.WeightMeans.Zip(communityExperiment.Posteriors.WeightPrecisions, (m, p) => new { m, p }).Select((ia, i) => new { ia, i })
            //  .OrderByDescending(x => Math.Abs(x.ia.m.GetMean())).ToList();
            // Console.WriteLine("Top 20 weights:\n {0}", string.Join("\n", topWeights.Take(20).Select(pair => string.Format("{0}: {1}", pair.i, new Gaussian(pair.ia.m.GetMean(), pair.ia.p.GetMean())))));

            // //communityExperiment.Posteriors.WeightPrecisions = DistributionArrayHelpers.Copy( priors.WeightPrecisions ).ToArray();
            var sourcePosteriors = new Marginals
            {
                WeightMeans      = communityExperiment.Posteriors.WeightMeans,
                WeightPrecisions = priors.WeightPrecisions, //communityExperiment.Posteriors.WeightMeans,
                Weights          = null
            };

            // Select half the features

            /*
             *          trainData.DataSet.Features = trainData.DataSet.Features.Select(
             *                  ia => ia.Select(
             *                          ib => topWeights.Take(topWeights.Count / 2).Select(pair => ib[pair.i]).ToArray())
             *                          .ToArray())
             *                  .ToArray();
             *
             *          // Retrain using these weights
             */

            // if (false)
            // {
            //  // Do online learning
            //  var onlineExperiment = new Experiment
            //  {
            //      TrainModel = trainModel,
            //      TestModel = testModel,
            //      Name = "Online"
            //  };

            //  onlineExperiment.RunOnline(testData.DataSet, testData.HoldoutSet, priors);

            //  // Do transfer learning
            //  var personalisationExperiment = new Experiment
            //  {
            //      TrainModel = trainModel,
            //      TestModel = testModel,
            //      Name = "Community"
            //  };

            //  personalisationExperiment.RunOnline(testData.DataSet, testData.HoldoutSet, communityExperiment.Posteriors);

            //  // Plot cumulative metrics
            //  Utils.PlotCumulativeMetrics(new [] { onlineExperiment, personalisationExperiment }, "Active", ShowPlots);
            // }

            // ACTIVE MODEL
            foreach (var doTransfer in new[] { false, true })
            {
                var experiments = new List <Experiment>();
                var learners    = CreateLearners(trainModel, testModel, evidenceModel, testData, testVOI, testActiveEvidence);

                foreach (var learner in learners)
                {
                    Console.WriteLine("Testing Active{0} Learning ({1})", doTransfer ? " Real Transfer" : "Real Online", learner.Key);
                    var experiment = new Experiment
                    {
                        TrainModel     = trainModel,
                        TestModel      = testModel,
                        Name           = learner.Key,
                        ActiveLearners = learner.Value
                    };

                    experiment.RunActive(testData.DataSet, testData.HoldoutSet, ActiveSteps, doTransfer ? sourcePosteriors : priors);
                    experiments.Add(experiment);

                    if (false)
                    {
                        Utils.PlotPosteriors(
                            experiment.IndividualPosteriors[0].WeightMeans,
                            experiment.IndividualPosteriors[0].WeightPrecisions,
                            null,
                            "Posterior weights for " + learner.Key + " " + (doTransfer ? " (transfer)" : ""),
                            "Feature",
                            ShowPlots);
                    }
                }

                Utils.PlotHoldoutMetrics(experiments, doTransfer ? "Real Active Transfer" : "Real Active", "", ShowPlots);
            }
        }