/// <summary>
        /// Gets a new Decision Vector, based on an average of the matching elements from each parent.
        /// </summary>
        /// <param name="parents">A list of parent <see cref="DecisionVector"/>s.</param>
        /// <returns>A new <see cref="DecisionVector"/>.</returns>
        /// <exception cref="ArgumentOutOfRangeException">
        /// Thrown if:
        /// - there are less than two parents; or
        /// - the parents have different length or zero length decision vectors; or
        /// - any of the parents have non-continuous Decision Vector elements.
        /// </exception>
        public DecisionVector Operate(params DecisionVector[] parents)
        {
            if (parents.Length < 2)
            {
                throw new ArgumentOutOfRangeException(nameof(parents),
                                                      "There must be at least two parents.");
            }

            if (parents.Any(p => p.GetContinuousElements().Count == 0))
            {
                throw new ArgumentOutOfRangeException(nameof(parents),
                                                      "Parents must have non-zero length decision vectors.");
            }

            if (parents.Any(p => p.GetContinuousElements().Count != parents.First().Count))
            {
                throw new ArgumentOutOfRangeException(nameof(parents),
                                                      "Parents must have the same length and fully continuous decision vectors.");
            }

            return(DecisionVector.CreateFromArray(
                       parents.First().GetDecisionSpace(),
                       parents
                       .Select(p => p.Select(v => (double)v))
                       .Aggregate((p1, p2) => p1.Select((v, i) => v + p2.ElementAt(i)))
                       .Select(v => v / parents.Length)));
        }
Beispiel #2
0
        /// <summary>
        /// Gets a new Decision Vector, based on selecting each element from one parent or the other.
        /// This selection can be biased towards the first parent (if <see cref="crossoverBias"/> is greater than 0.5)
        /// or towards the second parent (if <see cref="crossoverBias"/> is less than 0.5).
        /// </summary>
        /// <remarks>
        /// The two decision vectors can be different lengths.
        /// If so, for each element that only exists in the longer parent, if the shorter parent is selected,
        /// that element is removed.
        /// </remarks>
        /// <param name="parents">Two <see cref="DecisionVector"/>s to use as a parents.</param>
        /// <returns>A new <see cref="DecisionVector"/>.</returns>
        public DecisionVector Operate(params DecisionVector[] parents)
        {
            var firstParent  = parents[0];
            var secondParent = parents[1];

            var numDims = Math.Max(firstParent.Count, secondParent.Count);

            var dims      = new List <IVariable>();
            var newVector = new List <object>();

            for (var d = 0; d < numDims; d++)
            {
                var parentToUse = rngManager.Rng.NextDouble() < crossoverBias
                    ? firstParent
                    : secondParent;

                if (parentToUse.Count < (d + 1))
                {
                    continue;
                }

                dims.Add(parentToUse.GetDecisionSpace().ElementAt(d));
                newVector.Add(parentToUse.ElementAt(d));
            }

            return(DecisionVector.CreateFromArray(new DecisionSpace(dims), newVector));
        }
Beispiel #3
0
        /// <summary>
        /// Gets a new Decision Vector with elements which have potentially been mutated.
        /// Uses <see cref="IVariable"/> to wrap the added number, ensuring a valid Decision Vector is always created.
        /// </summary>
        /// <param name="decisionVector">The existing Decision Vector.</param>
        /// <returns>A new Decision Vector.</returns>
        public DecisionVector Operate(DecisionVector decisionVector)
        {
            var locationsToMutate = rngManager.GetLocations(
                decisionVector.Count, maximumNumberOfMutations,
                true, mutationProbability);

            var newDv = decisionVector.Select(i => (double)i).ToArray();
            var newDs = decisionVector.GetDecisionSpace();

            foreach (var location in locationsToMutate)
            {
                var mutation = rngManager.Rng.Next(
                    minimum, includeZero ? maximum : maximum - 1);
                if (!includeZero)
                {
                    if (mutation >= 0)
                    {
                        mutation += 1;
                    }
                }

                newDv[location] = Convert.ToDouble(newDs.ElementAt(location).AddOrWrap(newDv[location], mutation));
            }

            return(DecisionVector.CreateFromArray(newDs, newDv));
        }
Beispiel #4
0
        public void ThreeCitiesInATriangle_CorrectlyCalculatesDistances(params double[][] cityLocations)
        {
            var tsp = new TravellingSalesman("Test Triangle", cityLocations,
                                             DecisionVector.CreateFromArray(DecisionSpace.CreateForUniformIntArray(4, 0, 2), new[] { 0, 1, 2, 0 }));

            Assert.Equal(12.0, tsp.Evaluate(tsp.GetGlobalOptimum()).ElementAt(0));
        }
Beispiel #5
0
        public static List <Individual> CreateNewIndividualsFromArray(double[][] testValues)
        {
            var ds  = DecisionSpace.CreateForUniformDoubleArray(testValues.ElementAt(0).Length, double.MinValue, double.MaxValue);
            var dvs = testValues.Select(v => DecisionVector.CreateFromArray(ds, v));

            return(dvs.Select(v => new Individual(v)).ToList());
        }
Beispiel #6
0
        /// <summary>
        /// Gets a new Decision Vector where elements have potentially been mutated.
        /// Uses <see cref="IVariable"/> to implement the random number generation, so only valid individuals can be created.
        /// </summary>
        /// <param name="decisionVector">The existing Decision Vector.</param>
        /// <returns>A new <see cref="DecisionVector"/>.</returns>
        /// <exception cref="ArgumentException">Thrown when Decision Vector is zero length.</exception>
        public DecisionVector Operate(DecisionVector decisionVector)
        {
            if (decisionVector.Count == 0)
            {
                throw new ArgumentException("Decision Vector must not be empty.",
                                            nameof(decisionVector));
            }

            var locationsToMutate = rngManager.GetLocations(
                decisionVector.Count, maximumNumberOfMutations,
                true, mutationProbability);

            var newDv = new object[decisionVector.Count];
            var newDs = decisionVector.GetDecisionSpace();

            for (var i = 0; i < decisionVector.Count; i++)
            {
                // Variable may be mutated multiple times.
                var numTimesToMutate = locationsToMutate.Count(l => l == i);

                if (numTimesToMutate == 0)
                {
                    newDv[i] = decisionVector.ElementAt(i);
                }
                else
                {
                    for (var j = 0; j < numTimesToMutate; j++)
                    {
                        newDv[i] = newDs.ElementAt(i).GetNextRandom(rngManager.Rng);
                    }
                }
            }
            return(DecisionVector.CreateFromArray(newDs, newDv));
        }
Beispiel #7
0
        /// <summary>
        /// Gets a new Decision Vector whose elements have potentially been mutated.
        /// </summary>
        /// <param name="decisionVector">The existing Decision Vector.</param>
        /// <returns>A new Decision Vector.</returns>
        /// <exception cref="ArgumentException">Thrown when the Decision Vector has less than 2 elements.</exception>
        public DecisionVector Operate(DecisionVector decisionVector)
        {
            if (decisionVector.Count < 2)
            {
                throw new ArgumentException("Decision Vector must more than one element.",
                                            nameof(decisionVector));
            }

            if (rngManager.Rng.NextDouble() >= mutationProbability)
            {
                return(decisionVector);
            }

            var locationsToSwap = rngManager.GetLocations(
                decisionVector.Count, 2, false, 1);

            // New vector - swap elements
            var vector     = decisionVector.ToList();
            var firstItem  = vector.ElementAt(locationsToSwap.ElementAt(0));
            var secondItem = vector.ElementAt(locationsToSwap.ElementAt(1));

            vector.RemoveAt(locationsToSwap.ElementAt(0));
            vector.Insert(locationsToSwap.ElementAt(0), secondItem);
            vector.RemoveAt(locationsToSwap.ElementAt(1));
            vector.Insert(locationsToSwap.ElementAt(1), firstItem);

            // Assumption, we are swapping the values of the items, not the actual dimensions.
            return(DecisionVector.CreateFromArray(
                       decisionVector.GetDecisionSpace(),
                       vector));
        }
        /// <summary>
        /// Gets a new Decision Vector, based on simulating the operation of a single-point binary crossover.
        /// </summary>
        /// <param name="parents">Two <see cref="DecisionVector"/>s to use as a parents.</param>
        /// <returns>A new <see cref="DecisionVector"/>.</returns>
        public DecisionVector Operate(params DecisionVector[] parents)
        {
            if (parents[0].GetContinuousElements().Count == 0)
            {
                throw new ArgumentOutOfRangeException(nameof(parents),
                                                      "Parents must have non-zero length continuous Decision Vector.");
            }

            if (parents[1].GetContinuousElements().Count == 0)
            {
                throw new ArgumentOutOfRangeException(nameof(parents),
                                                      "Parents must have non-zero length continuous Decision Vector.");
            }

            var firstParent = Vector <double> .Build.DenseOfEnumerable(
                parents[0].GetContinuousElements().Select(d => (double)d));

            var secondParent = Vector <double> .Build.DenseOfEnumerable(
                parents[1].GetContinuousElements().Select(d => (double)d));

            // Multiply by -1 randomly to ensure either possibility is equally possible.
            var multiplier = rngManager.Rng.NextBoolean() ? -1 : 1;

            // Get beta value
            var beta = getBetaFromU(rngManager.Rng.NextDouble());

            // Create child
            var child = 0.5 * ((1 - beta * multiplier) * firstParent
                               + (1 + beta * multiplier) * secondParent);

            return(DecisionVector.CreateFromArray(parents[0].GetDecisionSpace(),
                                                  child.ToArray()));
        }
        public void TwoEqualVectors_WithSameSpace_AreEqual()
        {
            var values2 = exampleContinuousVector.ToArray();
            var dv1     = DecisionVector.CreateFromArray(continuousSpace, exampleContinuousVector);
            var dv2     = DecisionVector.CreateFromArray(continuousSpace, values2);

            Assert.True(dv1.Equals(dv2));
        }
Beispiel #10
0
        public void TwoDifferentVectors_WithSameSpace_AreNotEqual()
        {
            var values2 = exampleContinuousVector.Select(i => i - 1).ToArray();
            var dv1     = DecisionVector.CreateFromArray(continuousSpace, exampleContinuousVector);
            var dv2     = DecisionVector.CreateFromArray(continuousSpace, values2);

            Assert.False(dv1.Equals(dv2));
        }
Beispiel #11
0
        public void TwoEqualVectors_WithDifferentSpace_AreNotEqual()
        {
            var space2 = ObjectCreators.GetDecisionSpace(Dims, MinValueContinuous - 1, MaxValueContinuous + 1);
            var dv1    = DecisionVector.CreateFromArray(continuousSpace, exampleContinuousVector);
            var dv2    = DecisionVector.CreateFromArray(space2, exampleContinuousVector);

            Assert.False(dv1.Equals(dv2));
        }
Beispiel #12
0
        private bool replaceHyperParametersFrom(IEnumerable <IVariable> decisionSpace, IEnumerable <object> values)
        {
            HyperParameters = DecisionVector.CreateFromArray(
                new DecisionSpace(decisionSpace),
                values);

            return(true);
        }
Beispiel #13
0
        public void TwoDim_CorrectlyIdentifiesIllegalSolution()
        {
            var evaluator = new Ellipsoidal(2);
            var ds        = DecisionSpace.CreateForUniformDoubleArray(2, double.MinValue, double.MaxValue);
            var legal     = evaluator.GetLegality(DecisionVector.CreateFromArray(ds, new[] { 11.0, -12.0 }));

            Assert.False(legal);
        }
Beispiel #14
0
        public void TwoDim_EvaluatesCorrectValues(double[] values)
        {
            var evaluator = new Rastrigin(2);
            var ds        = evaluator.GetGlobalOptimum().GetDecisionSpace();
            var result    = evaluator.Evaluate(DecisionVector.CreateFromArray(ds, new[] { values[0], values[1] }));

            Assert.True(Math.Abs(values[2] - result.ElementAt(0)) < 0.001);
        }
Beispiel #15
0
        public void CreateInitialVertices_WithStepSizeZero_Throws()
        {
            var initialVertex = DecisionVector.CreateFromArray(
                DecisionSpace.CreateForUniformDoubleArray(3, double.MinValue, double.MaxValue),
                Enumerable.Repeat(0.0, 3));

            Assert.Throws <ArgumentOutOfRangeException>(() => Simplex.CreateInitialVertices(initialVertex, 0));
        }
 public MutationRandomSwapTests()
 {
     testDv = DecisionVector.CreateFromArray(
         DecisionSpace.CreateForUniformDoubleArray(8, double.MinValue, double.MaxValue),
         new double[8] {
         7, 6, 5, 4, 3, 2, 1, 0
     });
 }
Beispiel #17
0
        public void TwoDim_CorrectlyIdentifiesLegalSolution()
        {
            var evaluator = new Ellipsoidal(2);
            var ds        = evaluator.GetGlobalOptimum().GetDecisionSpace();
            var legal     = evaluator.GetLegality(DecisionVector.CreateFromArray(ds, new[] { 1.0, 1.0 }));

            Assert.True(legal);
        }
Beispiel #18
0
        public void TwoDim_EvaluatesCorrectValues(double[] values)
        {
            var evaluator = new Ellipsoidal(2);
            var ds        = evaluator.GetGlobalOptimum().GetDecisionSpace();
            var result    = evaluator.Evaluate(DecisionVector.CreateFromArray(ds, new[] { values[0], values[1] }));

            Assert.Equal(values[2], result.ElementAt(0));
        }
 public MutationReplaceWithRandomNumberTests()
 {
     testDv = DecisionVector.CreateFromArray(
         DecisionSpace.CreateForUniformDoubleArray(8, 0, 10),
         new double[8] {
         7, 6, 5, 4, 3, 2, 1, 0
     });
 }
Beispiel #20
0
 /// <summary>
 /// Creates an evaluator for the Rosenbrock Function.
 /// Assumes unconstrained, even though normally checked on a [-5, 10] basis.
 /// Global optimum is at [1,1,1,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public Rosenbrock(int numDims) : base(
         "Rosenbrock Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       double.MinValue, double.MaxValue,
                                                       -5.0, 10.0),
             Enumerable.Repeat(1.0, numDims).ToArray()))
 {
 }
Beispiel #21
0
        public void CorrectlyIdentifiesLegalSolution()
        {
            var evaluator = new Zdt3();
            var ds        = evaluator.GetOptimalParetoFront(1).ElementAt(0).GetDecisionSpace();
            var legal     = evaluator.GetLegality(DecisionVector.CreateFromArray(ds,
                                                                                 ds.Select(d => d.GetNextRandom(new SystemRandomSource()))));

            Assert.True(legal);
        }
Beispiel #22
0
 /// <summary>
 /// Creates an evaluator for Salomon's Function.
 /// Assumes unconstrained, even though normally checked on a +/-100 basis
 /// Global optimum is at [0,0,0,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public Salomon(int numDims) : base(
         "Salomon's Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       double.MinValue, double.MaxValue,
                                                       -100, 100),
             new double[numDims]))
 {
 }
Beispiel #23
0
 /// <summary>
 /// Creates an evaluator for the Generalised Rastrigin Function.
 /// Assumes unconstrained, even though normally checked on a +/-5.12 basis
 /// Global optimum is at [0,0,0,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public Rastrigin(int numDims) : base(
         "Generalised Rastrigin Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       double.MinValue, double.MaxValue,
                                                       -5.12, 5.12),
             new double[numDims]))
 {
 }
Beispiel #24
0
 /// <summary>
 /// Creates an evaluator for the Styblinski-Tang Function.
 /// Constrained on [-5, 5]
 /// Global optimum is at [-2.903534, -2.903534, -2.903534,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public StyblinskiTang(int numDims) : base(
         "Styblinski-Tang Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       -5, 5,
                                                       -4.5, 2.5),
             Enumerable.Repeat(-2.903534, numDims).ToArray()))
 {
 }
Beispiel #25
0
 /// <summary>
 /// Creates an evaluator for the Schwefel Function.
 /// Constrained on [-500, 500]
 /// Global optimum is at [420.9687, 420.9687, 420.9687,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public Schwefel(int numDims) : base(
         "Schwefel Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       -500.0, 500.0,
                                                       -250, 475),
             Enumerable.Repeat(420.9687, numDims).ToArray()))
 {
 }
Beispiel #26
0
        public void CorrectlyIdentifiesIllegalSolution()
        {
            var evaluator = new Zdt3();
            var ds        = DecisionSpace.CreateForUniformDoubleArray(30, -2, -1, -2, -1);
            var legal     = evaluator.GetLegality(DecisionVector.CreateFromArray(ds,
                                                                                 ds.Select(d => d.GetNextRandom(new SystemRandomSource()))));

            Assert.False(legal);
        }
Beispiel #27
0
 /// <summary>
 /// Creates an evaluator for the Ellipsoidal Function.
 /// Constrained on [-10, 10]
 /// Global optimum is at [0,0,0,...]
 /// </summary>
 /// <param name="numDims">Number of input dimensions</param>
 public Ellipsoidal(int numDims) : base(
         "Ellipsoidal Function",
         DecisionVector.CreateFromArray(
             DecisionSpace.CreateForUniformDoubleArray(numDims,
                                                       -10, 10,
                                                       -5, 5),
             new double[numDims]))
 {
 }
        public RandomNumberManagerTests()
        {
            testDv = DecisionVector.CreateFromArray(
                DecisionSpace.CreateForUniformIntArray(8, 0, 7),
                new int[8] {
                7, 6, 5, 4, 3, 2, 1, 0
            });

            rngManager = new RandomNumberManager(new MersenneTwister(123456789));
        }
Beispiel #29
0
        public CrossoverSimulatedBinaryTests()
        {
            var decisionSpaceUniform = DecisionSpace.CreateForUniformDoubleArray(
                4, double.MinValue, double.MaxValue);

            parent1 = DecisionVector.CreateFromArray(
                decisionSpaceUniform, new[] { 0.5, 1.5, 2.5, 3.5 });
            parent2 = DecisionVector.CreateFromArray(
                decisionSpaceUniform, new[] { 4.5, 3.5, 2.5, 1.5 });
        }
Beispiel #30
0
            private void updateDecisionVector(bool add = true)
            {
                var elements = decisionVector.Select(d => (double)d).ToList();

                elements[0] += add ? 0.01 : -0.01;
                var space = decisionVector.GetDecisionSpace();

                decisionVector = DecisionVector.CreateFromArray(
                    space, elements);
            }