protected void CrossSection(IChromosome firstParent, IChromosome secondParent, IChromosome firstChild, IChromosome secondChild, int sectionIndex) { var startIndex = sectionIndex * m_sectionSize; var useFirstParentFirst = false; if (m_randomParent) { useFirstParentFirst = RandomizationProvider.Current.GetInt(0, 2) == 0; } else { useFirstParentFirst = sectionIndex % 2 == 0; } if (useFirstParentFirst) { firstChild.ReplaceGenes(startIndex, firstParent.GetGenes().Skip(startIndex).Take(m_sectionSize).ToArray()); secondChild.ReplaceGenes(startIndex, secondParent.GetGenes().Skip(startIndex).Take(m_sectionSize).ToArray()); } else { firstChild.ReplaceGenes(startIndex, secondParent.GetGenes().Skip(startIndex).Take(m_sectionSize).ToArray()); secondChild.ReplaceGenes(startIndex, firstParent.GetGenes().Skip(startIndex).Take(m_sectionSize).ToArray()); } }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="leftParent">Left parent.</param> /// <param name="rightParent">Right parent.</param> private IChromosome CreateChild(IChromosome leftParent, IChromosome rightParent) { var firstCutGenesCount = SwapPointOneGeneIndex + 1; var secondCutGenesCount = SwapPointTwoGeneIndex + 1; var child = leftParent.CreateNew(); child.ReplaceGenes(0, leftParent.GetGenes().Take(firstCutGenesCount).ToArray()); child.ReplaceGenes(firstCutGenesCount, rightParent.GetGenes().Skip(firstCutGenesCount).Take(secondCutGenesCount - firstCutGenesCount).ToArray()); child.ReplaceGenes(secondCutGenesCount, leftParent.GetGenes().Skip(secondCutGenesCount).ToArray()); return(child); }
protected override void PerformMutate(IChromosome chromosome, float probability) { if (RandomizationProvider.Current.GetDouble() <= probability) { var genes = chromosome.GetGenes().ToList(); var geneIndex = RandomizationProvider.Current.GetInt(0, genes.Count); // Select two indexes within the trait group for swapping var i1 = RandomizationProvider.Current.GetInt(0, NumHouses); var i2 = RandomizationProvider.Current.GetInt(0, NumHouses); var(m1, m2) = i1 < i2 ? (i1, i2) : (i2, i1); var currVal = (int[])genes[geneIndex].Value; // TODO: Determine whether reverse sequence is better //var sequenceLength = m2 - m1 + 1; //var start = currVal.Take(m1); //var mid = currVal.Skip(m1).Take(sequenceLength).Reverse(); //var end = currVal.Skip(m2 + 1); //var newVal = start.Concat(mid).Concat(end).ToArray(); // Swap two values int[] newVal = new int[5]; Array.Copy(currVal, newVal, 5); newVal[m1] = currVal[m2]; newVal[m2] = currVal[m1]; chromosome.ReplaceGene(geneIndex, new Gene(newVal)); } }
/// <summary>Mutate the specified chromosome.</summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { if (!(chromosome is DoubleChromosome)) { throw new MutationException(this, "The Polynomial Mutation can be only used with double (floating point) chromosomes."); } if (RandomizationProvider.Current.GetDouble() <= probability) { Gene[] genes = chromosome.GetGenes(); double u = RandomizationProvider.Current.GetDouble(); if (u <= 0.5) { for (int i = 0; i < genes.Count(); i++) { double geneValue = (double)genes[i].Value; var delta = Math.Pow(2 * u, 1 / (DistributionIndex + 1)) - 1; chromosome.ReplaceGene(i, new Gene(geneValue + delta * (geneValue - ((DoubleChromosome)chromosome).MinValues[i]))); } } else { for (int i = 0; i < genes.Count(); i++) { double geneValue = (double)genes[i].Value; var delta = 1 - Math.Pow(2 * (1 - u), 1 / (DistributionIndex + 1)); chromosome.ReplaceGene(i, new Gene(geneValue + delta * (((DoubleChromosome)chromosome).MaxValues[i] - geneValue))); } } } }
/// <summary> /// Performs the evaluation against the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome to be evaluated.</param> /// <returns>The fitness of the chromosome.</returns> public double Evaluate(IChromosome chromosome) { var genes = chromosome.GetGenes(); var distanceSum = 0.0; var lastItemIndex = Convert.ToInt32(genes[0].Value, CultureInfo.InvariantCulture); var itemIndices = new List <int>(); foreach (var g in genes) { var currentItemIndex = Convert.ToInt32(g.Value, CultureInfo.InvariantCulture); distanceSum += Solution.DistanceMatrix[lastItemIndex, currentItemIndex]; lastItemIndex = currentItemIndex; itemIndices.Add(lastItemIndex); } distanceSum += Solution.DistanceMatrix[itemIndices.Last(), itemIndices.First()]; //var fitness = 1.0 - (distanceSum / (Items.Count * 1000.0)); //Used fitness function for TSP var fitness = (1.0 / distanceSum) * 1000; ((PickListGAChromosome)chromosome).Distance = distanceSum; if (fitness < 0) { fitness = 0; } return(fitness); }
public double Evaluate(IChromosome chromosome) { var m = this.maze.Copy(); var genes = chromosome.GetGenes(); var walker = new MazeWalker(m, genes); int repeatedSteps; int closest; var steps = walker.Walk(out repeatedSteps, out closest); if (steps < int.MaxValue) { steps = steps + repeatedSteps; } else { steps -= this.maze.Height * this.maze.Width * 50; // prevent overflow var open = 0; for (int x = 0; x < this.maze.Width; x++) { for (int y = 0; y < this.maze.Height; y++) { if (m[x, y] == Maze.State.Open) { open++; } } } steps += (open * 50) + ((int)closest * 2); } return(-(steps)); }
/// <summary> /// Mutate the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { if (RandomizationProvider.Current.GetFloat() < probability) { // Get size of deletion block and index of it int delSize = RandomizationProvider.Current.GetInt(MinDeletionSize, MaxDeletionSize); if (chromosome.Length - delSize <= 2) { return; } int index = RandomizationProvider.Current.GetInt(0, chromosome.Length - delSize - 1); // Get the genes as a list List <Gene> genes = new List <Gene>(); genes.AddRange(chromosome.GetGenes()); // Remove the given range genes.RemoveRange(index, delSize); // Resize the chromosome and replace with the mutated one chromosome.Resize(genes.Count); chromosome.ReplaceGenes(0, genes.ToArray()); } }
/// <summary> /// Mutate the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { if (RandomizationProvider.Current.GetFloat() < probability) { // Get random insertion size and index int insertionSize = RandomizationProvider.Current.GetInt(MinInsertionSize, MaxInsertionSize); int index = RandomizationProvider.Current.GetInt(0, chromosome.Length - 1); // Generate new genes for insertion List <Gene> newGenes = new List <Gene>(); for (int i = 0; i < insertionSize; i++) { newGenes.Add(chromosome.GenerateGene(index + i)); } // Get genes from chromosome and insert generated ones List <Gene> genes = new List <Gene>(); genes.AddRange(chromosome.GetGenes()); genes.InsertRange(index, newGenes); // Resize chromosome and replace with new chromosome.Resize(genes.Count); chromosome.ReplaceGenes(0, genes.ToArray()); } }
public double Evaluate(IChromosome chromosome) { var genes = chromosome.GetGenes(); double result = 0; for (int x1 = 0; x1 < genes.Length - 1; x1++) { int y1 = (int)genes[x1].Value; int sagdakiVezirSayisi = genes.Length - 1 - x1; for (int x2 = x1 + 1; x2 < genes.Length; x2++) { int y2 = (int)genes[x2].Value; if (y1 == y2 || x1 - y1 == x2 - y2 || x1 + y1 == x2 + y2) { sagdakiVezirSayisi -= 1; } } result += sagdakiVezirSayisi; } return(result); }
/// <summary> /// Creates the child. /// </summary> /// <param name="firstParent">First parent.</param> /// <param name="secondParent">Second parent.</param> /// <param name="swapIndexes">The swap indexes.</param> /// <returns> /// The child. /// </returns> protected override IChromosome CreateChild(IChromosome firstParent, IChromosome secondParent, int[] swapIndexes) { var secondParentSwapGenes = secondParent.GetGenes() .Select((g, i) => new { Gene = g, Index = i }) .Where((g) => swapIndexes.Contains(g.Index)) .ToArray(); var firstParentRemainingGenes = firstParent.GetGenes().Except(secondParentSwapGenes.Select(element => element.Gene).ToArray()).GetEnumerator(); var child = firstParent.CreateNew(); var secondParentSwapGensIndex = 0; for (int i = 0; i < firstParent.Length; i++) { if (secondParentSwapGenes.Any(f => f.Index == i)) { child.ReplaceGene(i, secondParentSwapGenes[secondParentSwapGensIndex++].Gene); } else { firstParentRemainingGenes.MoveNext(); child.ReplaceGene(i, firstParentRemainingGenes.Current); } } return(child); }
// Add fixed start point to beginning and end and apply permutation public Point[] GetPoints(IChromosome chromosome) => chromosome.GetGenes() .Select(x => (int)x.Value) .Prepend(0) .Append(0) .Select(x => InputPoints[x]) .ToArray();
private int calculateAttacks(IChromosome chromosome) { int collisions = 0; List <Gene> genePositions = chromosome.GetGenes().ToList(); List <int> positions = new List <int>(); foreach (Gene g in genePositions) { positions.Add(Convert.ToInt32(g.Value)); } for (int refQueen = 0; refQueen < positions.Count; refQueen++) { for (int targQueen = refQueen + 1; targQueen < positions.Count; targQueen++) { if (positions[refQueen] == positions[targQueen]) { collisions++; } else if ((positions[refQueen] - (targQueen - refQueen)) == positions[targQueen]) { collisions++; } else if ((positions[refQueen] + (targQueen - refQueen)) == positions[targQueen]) { collisions++; } } } // if (collisions == 0) // Console.WriteLine(String.Join("",positions)); return(collisions * -1); }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="firstParent">First parent.</param> /// <param name="secondParent">Second parent.</param> /// <param name="middleSectionBeginIndex">Middle section begin index.</param> /// <param name="middleSectionEndIndex">Middle section end index.</param> private static IChromosome CreateChild(IChromosome firstParent, IChromosome secondParent, int middleSectionBeginIndex, int middleSectionEndIndex) { var middleSectionGenes = firstParent.GetGenes().Skip(middleSectionBeginIndex).Take((middleSectionEndIndex - middleSectionBeginIndex) + 1); using (var secondParentRemainingGenes = secondParent.GetGenes().Except(middleSectionGenes).GetEnumerator()) { var child = firstParent.CreateNew(); for (int i = 0; i < firstParent.Length; i++) { var firstParentGene = firstParent.GetGene(i); if (i >= middleSectionBeginIndex && i <= middleSectionEndIndex) { child.ReplaceGene(i, firstParentGene); } else { secondParentRemainingGenes.MoveNext(); child.ReplaceGene(i, secondParentRemainingGenes.Current); } } return(child); } }
public double Evaluate(IChromosome chromosome) { List <GeneValue> genes = chromosome.GetGenes().Select(gene => gene.Value as GeneValue).ToList(); var result = genes .GroupBy(gene => gene.Profile) .Select(gene => new { Profile = gene.Key, Total = gene.Sum(x => x.Span.Length) }) .Select(r => new { Profile = r.Profile, Total = r.Total.MultiploSuperior(12) }) .ToList(); bool wrongProfile = false; genes.ForEach(gene => { if (!gene.Span.PossibleProfiles.Contains(gene.Profile)) { wrongProfile = true; } }); if (wrongProfile) { return((1 / result.Sum(r => r.Profile.Weight * r.Total)) * 0.01); } return(1 / result.Sum(r => r.Profile.Weight * r.Total)); }
public double Evaluate(IChromosome chromosome) { double fitness = -chromosome.GetGenes().Select(gene => Convert.ToInt32(gene.Value)).Sum(); Console.WriteLine($"[calculation] {fitness} for {chromosome.ToUserFriendly()}"); return(fitness); }
/// <summary> /// Mutate the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { ValidateLength(chromosome); double randomDouble = ThreadSafeRandom.ThisThreadsRandom.NextDouble(); //Console.WriteLine("Random Number generated to Mutate or Not: {0}", randomDouble); if (randomDouble <= probability) { //Console.WriteLine("...Sequence Mutation started..."); var indexes = Utils.GetUniqueInts(2, 0, chromosome.Length).OrderBy(i => i).ToArray(); //var indexes = new int[2] { 0, 1}; var firstIndex = indexes[0]; var secondIndex = indexes[1]; var sequenceLength = (secondIndex - firstIndex) + 1; //Console.WriteLine("Chromosome Before Mutation: [{0}]", string.Join(", ", Solution.extractChromosome(chromosome))); //Console.WriteLine("First Mutate Point Index: {0}", firstIndex); //Console.WriteLine("Second Mutate Point Index: {0}", secondIndex); var mutatedSequence = MutateOnSequence(chromosome.GetGenes().Skip(firstIndex).Take(sequenceLength)).ToArray(); chromosome.ReplaceGenes(firstIndex, mutatedSequence); //Console.WriteLine("Chromosome After Mutation: [{0}]", string.Join(", ", Solution.extractChromosome(chromosome))); //Console.WriteLine("...Sequence Mutation ended..."); } //else //{ // Console.WriteLine("No Mutation operation is done"); //} }
/// <summary> /// Mutate the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { if (RandomizationProvider.Current.GetFloat() < probability) { // Get slip size, source and destination indicies int slipSize = RandomizationProvider.Current.GetInt(MinSlipSize, Math.Min(MaxSlipSize, chromosome.Length)); int index = RandomizationProvider.Current.GetInt(0, chromosome.Length - (slipSize - 1)); float insertAfter = RandomizationProvider.Current.GetFloat(); // Get the genes in list form List <Gene> genes = new List <Gene>(); genes.AddRange(chromosome.GetGenes()); // Copy and insert a range as per above parameters if (insertAfter < 0.5f) { genes.InsertRange(index, genes.GetRange(index, slipSize)); } else { genes.InsertRange(index + slipSize, genes.GetRange(index, slipSize)); } // Resize and replace with new genome chromosome.Resize(genes.Count); chromosome.ReplaceGenes(0, genes.ToArray()); } }
/// <summary> /// Validates the chromosome. /// </summary> /// <param name="chromosome">The chromosomes.</param> public static void ValidateGenes(this IChromosome chromosome) { if (chromosome != null && chromosome.GetGenes().Any(g => g.Value == null)) { throw new InvalidOperationException("The chromosome '{0}' is generating genes with null value.".With(chromosome.GetType().Name)); } }
public double Evaluate(IChromosome chromosome) { Gene[] genes = chromosome.GetGenes(); double distanceSum = 0.0; int lastEdgeIndex = int.Parse(genes[0].Value.ToString()); // Węzeł początkowy int startingPoint = _edges[int.Parse(genes[0].Value.ToString())].VertexA; for (int i = 0; i < genes.Length; i++) { int edgeIndex = int.Parse(genes[i].Value.ToString()); Edge edge = _edges[edgeIndex]; // Znalezienie odwrotej krawędzi Edge reverseEdge = _edges.SingleOrDefault(e => e.VertexA == edge.VertexB && e.VertexB == edge.VertexA); // Oznaczenie krawędzi i jej odwrotności jako oznaczona edge.Visited = true; reverseEdge.Visited = true; if (i != 0 && edge.VertexA != _edges[int.Parse(genes[i - 1].Value.ToString())].VertexB) { // Jeśli ścieżka nie jest poprawna koszt jest znacząco zwiększany distanceSum += edge.Cost * 1000; lastEdgeIndex = edgeIndex; } else { distanceSum += edge.Cost; lastEdgeIndex = edgeIndex; } // Sprawdzenie czy ścieżka jest zamknięta i czy wszystkie krawędzie zostały odwiedzone if (AllEdgesVisited(_edges)) { if (edge.VertexB == startingPoint) { break; } Edge possibleEdge = _edges.SingleOrDefault(e => e.VertexA == edge.VertexB && e.VertexB == startingPoint); if (possibleEdge != null) { distanceSum += possibleEdge.Cost; break; } } } if (!AllEdgesVisited(_edges)) { distanceSum *= 1000; } _edges.ForEach(e => e.Visited = false); return(1.0 / distanceSum); }
private static Service[] GetServicesPlainList(IChromosome chromosome) { var services = chromosome.GetGenes() .Select(x => (Server)x.Value) .SelectMany(x => x.Services).ToArray(); return(services); }
private string GetServerNameByServiceId(Guid?serviceId, IChromosome parent) { var servers = parent.GetGenes() .Select(x => (Server)x.Value); var server = servers.First(x => x.Services.Any(s => s.Id == serviceId)); return(server.Name); }
public double Evaluate(IChromosome chromosome) { var genes = chromosome.GetGenes(); int guessValue = GuessNumberChromosome.ToGuessValue(genes); double fitness = 1.0 - (Math.Abs(this.finalAns - guessValue) / (double)this.maxDiffValue); return(fitness); }
/// <summary> /// Draws the sample. /// </summary> /// <param name="bestChromosome">The current best chromosome</param> public override void Draw(IChromosome bestChromosome) { var c = bestChromosome as TspChromosome; Console.WriteLine("Cities: {0:n0}", c.Length); Console.WriteLine("Distance: {0:n2}", c.Distance); var cities = bestChromosome.GetGenes().Select(g => g.Value.ToString()).ToArray(); Console.WriteLine("City tour: {0}", string.Join(", ", cities)); }
public double Evaluate(IChromosome chromosome) { // Evaluate the fitness of chromosome. var t = chromosome.GetGenes().ToList(); var summ = 0; t.ForEach(item => summ += (int)item.Value == 3 ? 1 : 100); Console.WriteLine("Evaluate end -> {0}", summ); return(summ); }
private static Maze FillMazeStepsWalked(Maze m, IChromosome chromosome) { var winnerSteps = m.Copy(); var w = new MazeWalker(winnerSteps, chromosome.GetGenes()); int repeatedSteps; int closest; w.Walk(out repeatedSteps, out closest); return(winnerSteps); }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="leftParent">Left parent.</param> /// <param name="rightParent">Right parent.</param> protected virtual IChromosome CreateChild(IChromosome leftParent, IChromosome rightParent) { var cutGenesCount = SwapPointIndex + 1; var child = leftParent.CreateNew(); child.ReplaceGenes(0, leftParent.GetGenes().Take(cutGenesCount).ToArray()); child.ReplaceGenes(cutGenesCount, rightParent.GetGenes().Skip(cutGenesCount).ToArray()); return(child); }
private static IChromosome CreateOffspring(IChromosome leftParent, IChromosome rightParent, int leftParentPoint, int rightParentPoint) { var offspring = leftParent.CreateNew(); offspring.Resize(leftParentPoint + (rightParent.Length - rightParentPoint)); offspring.ReplaceGenes(0, leftParent.GetGenes().Take(leftParentPoint).ToArray()); offspring.ReplaceGenes(leftParentPoint, rightParent.GetGenes().Skip(rightParentPoint).ToArray()); return(offspring); }
private static IChromosome CreateOffspring(IChromosome leftParent, IChromosome rightParent, int leftParentPoint, int rightParentPoint) { var offspring = leftParent.CreateNew(); offspring.Resize(leftParentPoint + (rightParent.Length - rightParentPoint)); offspring.ReplaceGenes(0, leftParent.GetGenes().Take(leftParentPoint).ToArray()); offspring.ReplaceGenes(leftParentPoint, rightParent.GetGenes().Skip(rightParentPoint).ToArray()); return offspring; }
private void fitnesstcheck(IChromosome chromosome) { var a = chromosome.GetGenes(); string s = ""; foreach (var b in a) { s = s + b.Value.ToString(); } ChromosomeDecode.checkstring(s); }
private static List <Server> GetEmptyServers(IChromosome chromosome) { var emptyServers = chromosome.GetGenes() .Select(x => { var server = (Server)x.Value; return(new Server(server.Name, server.Os, server.HddFull, server.RamFull)); }).ToList(); return(emptyServers); }
/// <summary> /// Make sure that gene is just replaced only if replaced one does not contain the same gene /// Ex: R(1,2,3) will ignore 3 and accept 4 /// </summary> /// <param name="replacedOne"></param> /// <param name="index"></param> /// <param name="gene"></param> /// <returns></returns> private bool SafeReplace(IChromosome replacedOne, int index, Gene gene) { bool hasAlreadyExist = replacedOne.GetGenes().Any(x => (x.Value as EmpScore).EmpId == (gene.Value as EmpScore).EmpId); if (!hasAlreadyExist) { replacedOne.ReplaceGene(index, gene); return(true); } return(false); }
public double Evaluate(IChromosome chromosome) { if (SupportsParallel) { Thread.Sleep (ParallelSleep); } var genes = chromosome.GetGenes(); double f = genes.Sum(g => (int) g.Value) / 20f; if(f > 1) { f = 0; } return f; }
/// <summary> /// Mutate the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome.</param> /// <param name="probability">The probability to mutate each chromosome.</param> protected override void PerformMutate(IChromosome chromosome, float probability) { if (chromosome.Length < 3) { throw new MutationException(this, "A chromosome should have, at least, 3 genes. {0} has only {1} gene.".With(chromosome.GetType().Name, chromosome.Length)); } if (RandomizationProvider.Current.GetDouble() <= probability) { var indexes = RandomizationProvider.Current.GetUniqueInts(2, 0, chromosome.Length).OrderBy(i => i).ToArray(); var firstIndex = indexes[0]; var secondIndex = indexes[1]; var revertedSequence = chromosome.GetGenes().Skip(firstIndex).Take((secondIndex - firstIndex) + 1).Reverse().ToArray(); chromosome.ReplaceGenes(firstIndex, revertedSequence); } }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="leftParent">Left parent.</param> /// <param name="rightParent">Right parent.</param> private IChromosome CreateChild(IChromosome leftParent, IChromosome rightParent) { var cutGenesCount = SwapPointIndex + 1; var child = leftParent.CreateNew(); child.ReplaceGenes(0, leftParent.GetGenes().Take(cutGenesCount).ToArray()); child.ReplaceGenes(cutGenesCount, rightParent.GetGenes().Skip(cutGenesCount).ToArray()); return child; }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="firstParent">First parent.</param> /// <param name="secondParent">Second parent.</param> /// <param name="middleSectionBeginIndex">Middle section begin index.</param> /// <param name="middleSectionEndIndex">Middle section end index.</param> private static IChromosome CreateChild(IChromosome firstParent, IChromosome secondParent, int middleSectionBeginIndex, int middleSectionEndIndex) { var middleSectionGenes = firstParent.GetGenes().Skip(middleSectionBeginIndex).Take((middleSectionEndIndex - middleSectionBeginIndex) + 1); var secondParentRemainingGenes = secondParent.GetGenes().Except(middleSectionGenes).GetEnumerator(); var child = firstParent.CreateNew(); for (int i = 0; i < firstParent.Length; i++) { var firstParentGene = firstParent.GetGene(i); if (i >= middleSectionBeginIndex && i <= middleSectionEndIndex) { child.ReplaceGene(i, firstParentGene); } else { secondParentRemainingGenes.MoveNext(); child.ReplaceGene(i, secondParentRemainingGenes.Current); } } return child; }
/// <summary> /// Performs the evaluation against the specified chromosome. /// </summary> /// <param name="chromosome">The chromosome to be evaluated.</param> /// <returns>The fitness of the chromosome.</returns> public double Evaluate(IChromosome chromosome) { var genes = chromosome.GetGenes (); var distanceSum = 0.0; var lastCityIndex = Convert.ToInt32 (genes [0].Value); var citiesIndexes = new List<int>(); citiesIndexes.Add(lastCityIndex); foreach (var g in genes) { var currentCityIndex = Convert.ToInt32 (g.Value); distanceSum += CalcDistanceTwoCities(Cities[currentCityIndex], Cities[lastCityIndex]); lastCityIndex = currentCityIndex; citiesIndexes.Add(lastCityIndex); } distanceSum += CalcDistanceTwoCities(Cities[citiesIndexes.Last()], Cities[citiesIndexes.First()]); var fitness = 1.0 - (distanceSum / (Cities.Count * 1000.0)); ((TspChromosome)chromosome).Distance = distanceSum; // There is repeated cities on the indexes? var diff = Cities.Count - citiesIndexes.Distinct ().Count (); if (diff > 0) { fitness /= diff; } if (fitness < 0) { fitness = 0; } return fitness; }
/// <summary> /// Creates the child. /// </summary> /// <returns>The child.</returns> /// <param name="leftParent">Left parent.</param> /// <param name="rightParent">Right parent.</param> protected override IChromosome CreateChild(IChromosome leftParent, IChromosome rightParent) { var firstCutGenesCount = SwapPointOneGeneIndex + 1; var secondCutGenesCount = SwapPointTwoGeneIndex + 1; var child = leftParent.CreateNew(); child.ReplaceGenes(0, leftParent.GetGenes().Take(firstCutGenesCount).ToArray()); child.ReplaceGenes(firstCutGenesCount, rightParent.GetGenes().Skip(firstCutGenesCount).Take(secondCutGenesCount - firstCutGenesCount).ToArray()); child.ReplaceGenes(secondCutGenesCount, leftParent.GetGenes().Skip(secondCutGenesCount).ToArray()); return child; }