public void PositionBasedCrossoverApplyTest()
        {
            TestRandom  random = new TestRandom();
            Permutation parent1, parent2, expected, actual;

            // The following test is based on an example from Larranaga, 1999. Genetic Algorithms for the Traveling Salesman Problem.
            random.Reset();
            random.IntNumbers = new int[] { 3, 1, 2, 5 };
            parent1           = new Permutation(PermutationTypes.RelativeUndirected, new int[] { 0, 1, 2, 3, 4, 5, 6, 7 });
            Assert.IsTrue(parent1.Validate());
            parent2 = new Permutation(PermutationTypes.RelativeUndirected, new int[] { 1, 3, 5, 7, 6, 4, 2, 0 });
            Assert.IsTrue(parent2.Validate());

            expected = new Permutation(PermutationTypes.RelativeUndirected, new int[] { 0, 3, 5, 1, 2, 4, 6, 7 });
            Assert.IsTrue(expected.Validate());
            actual = PositionBasedCrossover.Apply(random, parent1, parent2);
            Assert.IsTrue(actual.Validate());
            Assert.IsTrue(Auxiliary.PermutationIsEqualByPosition(expected, actual));

            // perform a test when two permutations are of unequal length
            random.Reset();
            bool exceptionFired = false;

            try {
                PositionBasedCrossover.Apply(random, new Permutation(PermutationTypes.RelativeUndirected, 8), new Permutation(PermutationTypes.RelativeUndirected, 6));
            }
            catch (System.ArgumentException) {
                exceptionFired = true;
            }
            Assert.IsTrue(exceptionFired);
        }
Ejemplo n.º 2
0
        public void Cross_ParentWithNoOrderedGenes_Exception()
        {
            var target = new PositionBasedCrossover();

            var chromosome1 = MockRepository.GenerateStub <ChromosomeBase>(10);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(8),
                new Gene(4),
                new Gene(7),
                new Gene(3),
                new Gene(6),
                new Gene(2),
                new Gene(5),
                new Gene(1),
                new Gene(9),
                new Gene(0)
            });
            chromosome1.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(10));

            var chromosome2 = MockRepository.GenerateStub <ChromosomeBase>(10);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(0),
                new Gene(1),
                new Gene(2),
                new Gene(3),
                new Gene(5),
                new Gene(5),
                new Gene(6),
                new Gene(7),
                new Gene(8),
                new Gene(9),
            });
            chromosome2.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(10));

            ExceptionAssert.IsThrowing(new CrossoverException(target, "The Position-based Crossover (POS) can be only used with ordered chromosomes. The specified chromosome has repeated genes."), () =>
            {
                target.Cross(new List <IChromosome>()
                {
                    chromosome1, chromosome2
                });
            });
        }
        public void Cross_ParentWithNoOrderedGenes_Exception()
        {
            var target = new PositionBasedCrossover();

            var chromosome1 = Substitute.For <ChromosomeBase>(10);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(8),
                new Gene(4),
                new Gene(7),
                new Gene(3),
                new Gene(6),
                new Gene(2),
                new Gene(5),
                new Gene(1),
                new Gene(9),
                new Gene(0)
            });
            chromosome1.CreateNew().Returns(Substitute.For <ChromosomeBase>(10));

            var chromosome2 = Substitute.For <ChromosomeBase>(10);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(0),
                new Gene(1),
                new Gene(2),
                new Gene(3),
                new Gene(5),
                new Gene(5),
                new Gene(6),
                new Gene(7),
                new Gene(8),
                new Gene(9),
            });
            chromosome2.CreateNew().Returns(Substitute.For <ChromosomeBase>(10));

            Assert.Catch <CrossoverException>(() =>
            {
                target.Cross(new List <IChromosome>()
                {
                    chromosome1, chromosome2
                });
            }, "The Position-based Crossover (POS) can be only used with ordered chromosomes. The specified chromosome has repeated genes.");
        }
Ejemplo n.º 4
0
        private void EvolveGeneticStrategyButton_Click(object sender, RoutedEventArgs e)
        {
            OutputTextBlock.Text = "Evolving...";

            Task.Run(() =>
            {
                var chromosome = new BlackjackChromosome();
                var fitness    = new BlackjackFitness();
                var population = new Population(Settings.GeneticSettings.MinPopulationSize, Settings.GeneticSettings.MaxPopulationSize, chromosome);

                ISelection selection;

                switch (Settings.GeneticSettings.SelectionType)
                {
                case SelectionType.Elite:
                    selection = new EliteSelection();
                    break;

                case SelectionType.RouletteWheel:
                    selection = new RouletteWheelSelection();
                    break;

                case SelectionType.StochasticUniversalSampling:
                    selection = new StochasticUniversalSamplingSelection();
                    break;

                case SelectionType.Tournament:
                    selection = new TournamentSelection(Settings.GeneticSettings.TournamentSize);
                    break;

                default:
                    throw new InvalidOperationException();
                }

                ICrossover crossover;

                switch (Settings.GeneticSettings.CrossoverType)
                {
                case CrossoverType.AlternatingPosition:
                    crossover = new AlternatingPositionCrossover();
                    break;

                case CrossoverType.CutAndSplice:
                    crossover = new CutAndSpliceCrossover();
                    break;

                case CrossoverType.Cycle:
                    crossover = new CycleCrossover();
                    break;

                case CrossoverType.OnePoint:
                    crossover = new OnePointCrossover();
                    break;

                case CrossoverType.TwoPoint:
                    crossover = new TwoPointCrossover();
                    break;

                case CrossoverType.OrderBased:
                    crossover = new OrderBasedCrossover();
                    break;

                case CrossoverType.Ordered:
                    crossover = new OrderedCrossover();
                    break;

                case CrossoverType.PartiallyMapped:
                    crossover = new PartiallyMappedCrossover();
                    break;

                case CrossoverType.PositionBased:
                    crossover = new PositionBasedCrossover();
                    break;

                case CrossoverType.ThreeParent:
                    crossover = new ThreeParentCrossover();
                    break;

                case CrossoverType.Uniform:
                    crossover = new UniformCrossover(Settings.Current.GeneticSettings.MixProbability);
                    break;

                case CrossoverType.VotingRecombination:
                    crossover = new VotingRecombinationCrossover();
                    break;

                default:
                    throw new InvalidOperationException();
                }

                var mutation     = new UniformMutation();
                var termination  = new FitnessStagnationTermination(Settings.Current.GeneticSettings.NumStagnantGenerations);
                var taskExecutor = new ParallelTaskExecutor();

                var ga = new GeneticAlgorithm(
                    population,
                    fitness,
                    selection,
                    crossover,
                    mutation);

                ga.Termination          = termination;
                ga.TaskExecutor         = taskExecutor;
                ga.MutationProbability  = Settings.GeneticSettings.MutationProbability;
                ga.CrossoverProbability = Settings.GeneticSettings.CrossoverProbability;

                var latestFitness = double.MinValue;

                ga.GenerationRan += (s, o) =>
                {
                    geneticStrategy = (IStrategy)ga.BestChromosome;

                    var generationNumber = ga.GenerationsNumber;
                    var bestFitness      = ga.BestChromosome.Fitness.Value;
                    var avgFitness       = ga.Population.CurrentGeneration.Chromosomes.Average(c => c.Fitness.Value);

                    Dispatcher.Invoke(() =>
                    {
                        if (generationNumber == 1)
                        {
                            OutputTextBlock.Text = string.Empty;
                        }

                        OutputTextBlock.Text = $"Gen: {generationNumber}\tFit: {bestFitness}\tAvg: {avgFitness.ToString("0")}\n" + OutputTextBlock.Text;

                        if (bestFitness != latestFitness)
                        {
                            latestFitness = bestFitness;

                            var savedImageName = Settings.Current.GeneticSettings.SaveImagePerGeneration ? "gen" + generationNumber : null;

                            StrategyViewer.Draw(GeneticStrategyCanvas, geneticStrategy, $"Best from generation {generationNumber}", savedImageName);
                        }
                    }, DispatcherPriority.Background);
                };

                ga.TerminationReached += (s, o) =>
                {
                    Dispatcher.Invoke(() =>
                    {
                        OutputTextBlock.Text = "Termination reached.\n" + OutputTextBlock.Text;
                        TestGeneticStrategyButton.IsEnabled = true;
                    }, DispatcherPriority.Background);
                };

                ga.Start();
            });
        }
Ejemplo n.º 5
0
        private static IAlgoritmo CriaAlgoritmoGenetico(Dictionary <string, string[]> dict, List <string> flat, Problema problema)
        {
            int         populacaoMin, populacaoMax;
            IPopulation population;

            ISelection   selection;
            ICrossover   crossover;
            IMutation    mutation;
            ITermination termination;
            IReinsertion reinsertion;
            float        crossoverProbability, mutationProbability;



            var p = dict.ValueOrDefault("p", "50,100").Split(new[] { ',' });

            if (p.Length != 2 || !int.TryParse(p[0], out populacaoMin) || !int.TryParse(p[1], out populacaoMax))
            {
                throw new ArgumentException("Faixa de população inválida.");
            }

            population = new Population(populacaoMin, populacaoMax, new CromossomoViajante(problema.Mapa.Locais.Count));

            switch (dict.ValueOrDefault("s", "t"))
            {
            case "e":
                selection = new EliteSelection();
                break;

            case "r":
                selection = new RouletteWheelSelection();
                break;

            case "s":
                selection = new StochasticUniversalSamplingSelection();
                break;

            case "t":
                selection = new TournamentSelection();
                break;

            default:
                throw new ArgumentException("Seleção inválida.");
            }

            switch (dict.ValueOrDefault("c", "o"))
            {
            case "s":
                crossover = new CutAndSpliceCrossover();
                break;

            case "c":
                crossover = new CycleCrossover();
                break;

            case "o":
                crossover = new OrderedCrossover();
                break;

            case "ob":
                crossover = new OrderBasedCrossover();
                break;

            case "op":
                crossover = new OnePointCrossover();
                break;

            case "pm":
                crossover = new PartiallyMappedCrossover();
                break;

            case "p":
                crossover = new PositionBasedCrossover();
                break;

            case "tpa":
                crossover = new ThreeParentCrossover();
                break;

            case "tp":
                crossover = new TwoPointCrossover();
                break;

            case "u":
                crossover = new UniformCrossover();
                break;

            default:
                throw new ArgumentException("Crossover inválido.");
            }

            switch (dict.ValueOrDefault("m", "r"))
            {
            case "d":
                mutation = new DisplacementMutation();
                break;

            case "f":
                mutation = new FlipBitMutation();
                break;

            case "i":
                mutation = new InsertionMutation();
                break;

            case "s":
                mutation = new PartialShuffleMutation();
                break;

            case "r":
                mutation = new ReverseSequenceMutation();
                break;

            case "t":
                mutation = new TworsMutation();
                break;

            case "u":
                mutation = new UniformMutation();
                break;

            default:
                throw new ArgumentException("Mutação inválida.");
            }

            switch (dict.ValueOrDefault("t", "s"))
            {
            case "s":
                termination = new FitnessStagnationTermination();
                break;

            case "t":
                termination = new FitnessThresholdTermination();
                break;

            case "g":
                termination = new GenerationNumberTermination();
                break;

            default:
                throw new ArgumentException("Terminação inválida.");
            }

            switch (dict.ValueOrDefault("e", "e"))
            {
            case "e":
                reinsertion = new ElitistReinsertion();
                break;

            case "p":
                reinsertion = new PureReinsertion();
                break;

            case "u":
                reinsertion = new UniformReinsertion();
                break;

            default:
                throw new ArgumentException("Reinserção inválida.");
            }

            if (!float.TryParse(dict.ValueOrDefault("cp", "0,75"), out crossoverProbability))
            {
                throw new ArgumentException("Probabilidade de crossover inválida.");
            }

            if (!float.TryParse(dict.ValueOrDefault("mp", "0,25"), out mutationProbability))
            {
                throw new ArgumentException("Probabilidade de mutação inválida.");
            }


            return(new AlgoritmoGenetico(problema, population, selection, crossover, crossoverProbability, mutation, mutationProbability, termination, reinsertion));
        }
Ejemplo n.º 6
0
        public void Cross_ParentsWith8Genes_Cross()
        {
            var target = new PositionBasedCrossover();

            // 1 2 3 4 5 6 7 8
            var chromosome1 = MockRepository.GenerateStub <ChromosomeBase>(8);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(1),
                new Gene(2),
                new Gene(3),
                new Gene(4),
                new Gene(5),
                new Gene(6),
                new Gene(7),
                new Gene(8)
            });
            chromosome1.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(8));

            // 2 4 6 8 7 5 3 1
            var chromosome2 = MockRepository.GenerateStub <ChromosomeBase>(8);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(2),
                new Gene(4),
                new Gene(6),
                new Gene(8),
                new Gene(7),
                new Gene(5),
                new Gene(3),
                new Gene(1)
            });
            chromosome2.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(8));

            // Child one: 1 4 6 2 3 5 7 8
            // Child two: 4 2 3 8 7 6 5 1
            var rnd = MockRepository.GenerateMock <IRandomization>();

            rnd.Expect(r => r.GetInt(1, 7)).Return(3);
            rnd.Expect(r => r.GetUniqueInts(3, 0, 8)).Return(new int[] { 1, 2, 5 });
            RandomizationProvider.Current = rnd;

            IList <IChromosome> actual = null;;

            TimeAssert.LessThan(40, () =>
            {
                actual = target.Cross(new List <IChromosome>()
                {
                    chromosome1, chromosome2
                });
            });

            Assert.AreEqual(2, actual.Count);
            var childOne = actual [0];
            var childTwo = actual [1];

            Assert.AreEqual(8, childOne.Length);
            Assert.AreEqual(8, childTwo.Length);

            Assert.AreEqual(8, childOne.GetGenes().Distinct().Count());
            Assert.AreEqual(8, childTwo.GetGenes().Distinct().Count());

            Assert.AreEqual(1, childOne.GetGene(0).Value);
            Assert.AreEqual(4, childOne.GetGene(1).Value);
            Assert.AreEqual(6, childOne.GetGene(2).Value);
            Assert.AreEqual(2, childOne.GetGene(3).Value);
            Assert.AreEqual(3, childOne.GetGene(4).Value);
            Assert.AreEqual(5, childOne.GetGene(5).Value);
            Assert.AreEqual(7, childOne.GetGene(6).Value);
            Assert.AreEqual(8, childOne.GetGene(7).Value);

            Assert.AreEqual(4, childTwo.GetGene(0).Value);
            Assert.AreEqual(2, childTwo.GetGene(1).Value);
            Assert.AreEqual(3, childTwo.GetGene(2).Value);
            Assert.AreEqual(8, childTwo.GetGene(3).Value);
            Assert.AreEqual(7, childTwo.GetGene(4).Value);
            Assert.AreEqual(6, childTwo.GetGene(5).Value);
            Assert.AreEqual(5, childTwo.GetGene(6).Value);
            Assert.AreEqual(1, childTwo.GetGene(7).Value);
        }
        public void Cross_ParentsWith6Genes_Cross()
        {
            var target = new PositionBasedCrossover();

            // 1 5 4 0 3 2
            var chromosome1 = MockRepository.GenerateStub <ChromosomeBase>(6);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(1),
                new Gene(5),
                new Gene(4),
                new Gene(0),
                new Gene(3),
                new Gene(2)
            });
            chromosome1.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(6));

            // 2 3 5 0 1 4
            var chromosome2 = MockRepository.GenerateStub <ChromosomeBase>(6);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(2),
                new Gene(3),
                new Gene(5),
                new Gene(0),
                new Gene(1),
                new Gene(4)
            });
            chromosome2.Expect(c => c.CreateNew()).Return(MockRepository.GenerateStub <ChromosomeBase>(6));

            // Child one: 4 3 5 0 1 2
            // Child two: 2 5 4 0 3 1
            var rnd = MockRepository.GenerateMock <IRandomization>();

            rnd.Expect(r => r.GetInt(1, 5)).Return(3);
            rnd.Expect(r => r.GetUniqueInts(3, 0, 6)).Return(new int[] { 2, 4, 3 });
            RandomizationProvider.Current = rnd;

            IList <IChromosome> actual = null;;

            TimeAssert.LessThan(40, () =>
            {
                actual = target.Cross(new List <IChromosome>()
                {
                    chromosome1, chromosome2
                });
            });

            Assert.AreEqual(2, actual.Count);
            var childOne = actual[0];
            var childTwo = actual[1];

            Assert.AreEqual(6, childOne.Length);
            Assert.AreEqual(6, childTwo.Length);

            Assert.AreEqual(6, childOne.GetGenes().Distinct().Count());
            Assert.AreEqual(6, childTwo.GetGenes().Distinct().Count());

            Assert.AreEqual(4, childOne.GetGene(0).Value);
            Assert.AreEqual(3, childOne.GetGene(1).Value);
            Assert.AreEqual(5, childOne.GetGene(2).Value);
            Assert.AreEqual(0, childOne.GetGene(3).Value);
            Assert.AreEqual(1, childOne.GetGene(4).Value);
            Assert.AreEqual(2, childOne.GetGene(5).Value);

            Assert.AreEqual(2, childTwo.GetGene(0).Value);
            Assert.AreEqual(5, childTwo.GetGene(1).Value);
            Assert.AreEqual(4, childTwo.GetGene(2).Value);
            Assert.AreEqual(0, childTwo.GetGene(3).Value);
            Assert.AreEqual(3, childTwo.GetGene(4).Value);
            Assert.AreEqual(1, childTwo.GetGene(5).Value);
        }
        public void Cross_ParentsWith8Genes_Cross()
        {
            var target = new PositionBasedCrossover();

            // 1 2 3 4 5 6 7 8
            var chromosome1 = Substitute.For <ChromosomeBase>(8);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(1),
                new Gene(2),
                new Gene(3),
                new Gene(4),
                new Gene(5),
                new Gene(6),
                new Gene(7),
                new Gene(8)
            });
            chromosome1.CreateNew().Returns(Substitute.For <ChromosomeBase>(8));

            // 2 4 6 8 7 5 3 1
            var chromosome2 = Substitute.For <ChromosomeBase>(8);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(2),
                new Gene(4),
                new Gene(6),
                new Gene(8),
                new Gene(7),
                new Gene(5),
                new Gene(3),
                new Gene(1)
            });
            chromosome2.CreateNew().Returns(Substitute.For <ChromosomeBase>(8));

            // Child one: 1 4 6 2 3 5 7 8
            // Child two: 4 2 3 8 7 6 5 1
            var rnd = Substitute.For <IRandomization>();

            rnd.GetInt(1, 7).Returns(3);
            rnd.GetUniqueInts(3, 0, 8).Returns(new int[] { 1, 2, 5 });
            RandomizationProvider.Current = rnd;

            var actual = target.Cross(new List <IChromosome>()
            {
                chromosome1, chromosome2
            });

            Assert.AreEqual(2, actual.Count);
            var childOne = actual [0];
            var childTwo = actual [1];

            Assert.AreEqual(8, childOne.Length);
            Assert.AreEqual(8, childTwo.Length);

            Assert.AreEqual(8, childOne.GetGenes().Distinct().Count());
            Assert.AreEqual(8, childTwo.GetGenes().Distinct().Count());

            Assert.AreEqual(1, childOne.GetGene(0).Value);
            Assert.AreEqual(4, childOne.GetGene(1).Value);
            Assert.AreEqual(6, childOne.GetGene(2).Value);
            Assert.AreEqual(2, childOne.GetGene(3).Value);
            Assert.AreEqual(3, childOne.GetGene(4).Value);
            Assert.AreEqual(5, childOne.GetGene(5).Value);
            Assert.AreEqual(7, childOne.GetGene(6).Value);
            Assert.AreEqual(8, childOne.GetGene(7).Value);

            Assert.AreEqual(4, childTwo.GetGene(0).Value);
            Assert.AreEqual(2, childTwo.GetGene(1).Value);
            Assert.AreEqual(3, childTwo.GetGene(2).Value);
            Assert.AreEqual(8, childTwo.GetGene(3).Value);
            Assert.AreEqual(7, childTwo.GetGene(4).Value);
            Assert.AreEqual(6, childTwo.GetGene(5).Value);
            Assert.AreEqual(5, childTwo.GetGene(6).Value);
            Assert.AreEqual(1, childTwo.GetGene(7).Value);
        }
        public void Cross_ParentsWith6Genes_Cross()
        {
            var target = new PositionBasedCrossover();

            // 1 5 4 0 3 2
            var chromosome1 = Substitute.For <ChromosomeBase>(6);

            chromosome1.ReplaceGenes(0, new Gene[] {
                new Gene(1),
                new Gene(5),
                new Gene(4),
                new Gene(0),
                new Gene(3),
                new Gene(2)
            });
            chromosome1.CreateNew().Returns(Substitute.For <ChromosomeBase>(6));

            // 2 3 5 0 1 4
            var chromosome2 = Substitute.For <ChromosomeBase>(6);

            chromosome2.ReplaceGenes(0, new Gene[]
            {
                new Gene(2),
                new Gene(3),
                new Gene(5),
                new Gene(0),
                new Gene(1),
                new Gene(4)
            });
            chromosome2.CreateNew().Returns(Substitute.For <ChromosomeBase>(6));

            // Child one: 4 3 5 0 1 2
            // Child two: 2 5 4 0 3 1
            var rnd = Substitute.For <IRandomization>();

            rnd.GetInt(1, 5).Returns(3);
            rnd.GetUniqueInts(3, 0, 6).Returns(new int[] { 2, 4, 3 });
            RandomizationProvider.Current = rnd;

            var actual = target.Cross(new List <IChromosome>()
            {
                chromosome1, chromosome2
            });

            Assert.AreEqual(2, actual.Count);
            var childOne = actual[0];
            var childTwo = actual[1];

            Assert.AreEqual(6, childOne.Length);
            Assert.AreEqual(6, childTwo.Length);

            Assert.AreEqual(6, childOne.GetGenes().Distinct().Count());
            Assert.AreEqual(6, childTwo.GetGenes().Distinct().Count());

            Assert.AreEqual(4, childOne.GetGene(0).Value);
            Assert.AreEqual(3, childOne.GetGene(1).Value);
            Assert.AreEqual(5, childOne.GetGene(2).Value);
            Assert.AreEqual(0, childOne.GetGene(3).Value);
            Assert.AreEqual(1, childOne.GetGene(4).Value);
            Assert.AreEqual(2, childOne.GetGene(5).Value);

            Assert.AreEqual(2, childTwo.GetGene(0).Value);
            Assert.AreEqual(5, childTwo.GetGene(1).Value);
            Assert.AreEqual(4, childTwo.GetGene(2).Value);
            Assert.AreEqual(0, childTwo.GetGene(3).Value);
            Assert.AreEqual(3, childTwo.GetGene(4).Value);
            Assert.AreEqual(1, childTwo.GetGene(5).Value);
        }
Ejemplo n.º 10
0
        public IList <IChromosome> PositionBasedCrossover()
        {
            var target = new PositionBasedCrossover();

            return(target.Cross(CreateTwoParents()));
        }