public void InitialisePopulation() { if (Configuration.POPULATION_FILE != String.Empty) { Console.Write("Loading Initial Population... "); members = Serializer.DeserializePopulation(new StreamReader(Configuration.POPULATION_FILE)); Console.WriteLine("Done"); } else { int POPULATION_SIZE = Configuration.POPULATION_SIZE; Console.WriteLine("Generating Initial Population... (0/" + POPULATION_SIZE + ")"); members = new PopulationMember[POPULATION_SIZE]; for (int i = 0; i < members.Length; i++) { do { members [i] = new PopulationMember(); } while (members[i].calculateFitness() == 0); //Console.SetCursorPosition (0, 0); //Console.Write ("Generating Initial Population... (" + i + "/" + INITIAL_POPULATION_SIZE + ")"); } //Console.SetCursorPosition (0, 0); Console.WriteLine("Generating Initial Population... Completed "); Console.Write("Saving Population... "); Serializer.SerializePopulation(members, new StreamWriter("LASTPOP_" + POPULATION_SIZE.ToString() + ".TXT", false)); Serializer.SerializePopulation(members, new StreamWriter("LASTPOP.TXT", false)); Console.WriteLine("Done"); } }
private List <PopulationMember> addCrossoverMembers(List <PopulationMember> newPop, int numberToAdd) { //Console.WriteLine ("Beginning Crossover"); // The fittest members have are more likely to be crossed (likelihood is proportional to their fitness) List <int> probabilityArray = new List <int> (); //Console.WriteLine ("Caluclating Probability Array..."); for (int x = 0; x < newPop.Count; x++) { for (int i = 0; i < newPop[x].lastFitness; i++) { probabilityArray.Add(x); } } for (int i = 0; i < numberToAdd; i++) { PopulationMember[] parents = new PopulationMember[Configuration.CROSSOVER_PARENT_COUNT]; for (int x = 0; x < parents.Length; x++) { parents [x] = newPop[probabilityArray [generator.next(0, probabilityArray.Count)]]; } //Console.WriteLine ("{4}/{5}: Crossing {0} (fitness {1}) and {2} (fitness {3})", first, newPop[first].lastFitness, second, newPop[second].lastFitness, i, numberToAdd); // Mutate crossover members PopulationMember newMember = crosser.crossover(parents); newMember = mutator.mutate(newMember); // With a certain probability, the crossover will be dismissed and a brand new population member introduced if (generator.next(0, Configuration.NEW_DURING_MUTATION_INVERSE) == 0) { PopulationMember p = new PopulationMember(); while (p.calculateFitness() < 1) { p = new PopulationMember(); } newPop.Add(p); } else { newPop.Add(newMember); } //newPop.Add(crosser.crossover (newPop[first], newPop[second])); } return(newPop); }
public PopulationMember[] select(PopulationMember[] current) { List <int> distList = new List <int> (); int added = 0; int toAdd = (int)Math.Round(current.Length * PROPORTION_TO_PICK, 0); PopulationMember[] pNew = new PopulationMember[toAdd]; // Find the max fitness int fitness = 0; for (int x = 0; x < current.Length; x++) { if (current[x].lastFitness > fitness) { fitness = current[x].lastFitness; added = 0; } if (added < pNew.Length && current [x].lastFitness == fitness) { pNew [added] = current [x]; added++; } } for (int i = 0; i < current.Length; i++) { if (current [i].lastFitness != fitness) { for (int x = 0; x < current [i].lastFitness * current[i].lastFitness; x++) { distList.Add(i); } } } for (int i = added; i < pNew.Length; i++) { pNew [i] = current [distList[_generator.next(0, distList.Count)]]; } return(pNew); }
public PopulationMember[] select(PopulationMember[] current) { //Console.WriteLine("Selecting fittest population members..."); Array.Sort(current); int min = current[current.Length - 1].lastFitness; int knownMin = 1; for (int i = current.Length - 2; i >= 0; i--) { if (current[i].lastFitness != min) { break; } else { knownMin++; } } int required = (int)Math.Round(PROPORTION_TO_PICK * current.Length, 0); int usable = current.Length - knownMin; int toAddAtRandom = required - usable; //Console.WriteLine ("Required: {0}, Usable: {1}, To Randomly Select: {2}", required, usable, toAddAtRandom); PopulationMember[] newPop = new PopulationMember[required]; // Add the top n that aren't the lowest fitness in the group for (int i = 0; i < usable && i < required; i++) { newPop[i] = current[i]; } //Console.WriteLine ("Added usable members"); // Randomly choose the remaining from the lowest fitness population members for (int i = usable; i < usable + toAddAtRandom; i++) { int n = _generator.next(usable, current.Length); newPop[i] = current[n]; } //Console.WriteLine ("Added random members"); return(newPop); }
public PopulationMember crossover(PopulationMember[] parent) { PopulationMember first = parent [0]; PopulationMember second = parent [1]; int shortest = first.parameters.Length > second.parameters.Length ? second.parameters.Length : first.parameters.Length; int crossoverPoint = _generator.next(4, shortest); while (crossoverPoint % 4 != 0) { crossoverPoint--; } List <int> firstList = new List <int> (); List <int> secondList = new List <int> (); for (int i = 0; i < crossoverPoint; i++) { firstList.Add(first.parameters [i]); secondList.Add(second.parameters [i]); } for (int i = crossoverPoint; i < second.parameters.Length; i++) { firstList.Add(second.parameters [i]); } for (int i = crossoverPoint; i < first.parameters.Length; i++) { secondList.Add(first.parameters [i]); } // Choose at random which to go with PopulationMember p = new PopulationMember(); if (_generator.next(0, 2) == 0) { p.parameters = firstList.ToArray(); } else { p.parameters = secondList.ToArray(); } return(p); }
public PopulationMember[] select(PopulationMember[] current) { List <int> distList = new List <int> (); for (int i = 0; i < current.Length; i++) { for (int x = 0; x < current [i].lastFitness * current[i].lastFitness; x++) { distList.Add(i); } } int toAdd = (int)Math.Round(current.Length * PROPORTION_TO_PICK, 0); PopulationMember[] pNew = new PopulationMember[toAdd]; for (int i = 0; i < pNew.Length; i++) { pNew [i] = current [distList[_generator.next(0, distList.Count)]]; } return(pNew); }
public PopulationMember mutate(PopulationMember member) { PopulationMember newMember = new PopulationMember(); newMember.parameters = member.parameters; for (int i = 0; i < member.parameters.Length; i += 4) { if (_generator.next(0, MUTATION_PROBABILITY_INVERSE) == 0) { switch (_generator.next(0, 8)) { case 0: //right newMember.parameters [i]++; newMember.parameters [i + 2]++; break; case 1: //down newMember.parameters [i + 1]--; newMember.parameters [i + 3]--; break; case 2: //left newMember.parameters [i]--; newMember.parameters [i + 2]--; break; case 3: //up newMember.parameters [i + 1]++; newMember.parameters [i + 3]++; break; case 4: //up-right newMember.parameters [i]++; newMember.parameters [i + 1]++; newMember.parameters [i + 2]++; newMember.parameters [i + 3]++; break; case 5: //down-right newMember.parameters [i]++; newMember.parameters [i + 1]--; newMember.parameters [i + 2]++; newMember.parameters [i + 3]--; break; case 6: //down-left newMember.parameters [i]--; newMember.parameters [i + 1]--; newMember.parameters [i + 2]--; newMember.parameters [i + 3]--; break; case 7: //up-left newMember.parameters [i]--; newMember.parameters [i + 1]++; member.parameters [i + 2]--; member.parameters [i + 3]++; break; } } } return(newMember); }
public PopulationMember mutate(PopulationMember member) { PopulationMember newMember = new PopulationMember(); newMember.parameters = member.parameters; int shiftAmount = _generator.next(0, 10) - 5; // Move up to 5 in either direction for (int i = 0; i < member.parameters.Length; i += 4) { if (_generator.next(0, MUTATION_PROBABILITY_INVERSE) == 0) { switch (_generator.next(0, 8)) { case 0: //right newMember.parameters [i] += shiftAmount; newMember.parameters [i + 2] += shiftAmount; break; case 1: //down newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 2: //left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 2] -= shiftAmount; break; case 3: //up newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; case 4: //up-right newMember.parameters [i] += shiftAmount; newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 2] += shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; case 5: //down-right newMember.parameters [i]++; newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 2] += shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 6: //down-left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 2] -= shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 7: //up-left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 2] -= shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; } Direction newDir = (Direction)(_generator.next(0, 8)); Direction currentDir = determineDirection(newMember.parameters, i); int[] parameters = newMember.parameters; changeDirection(ref parameters, i, currentDir, newDir); newMember.parameters = parameters; } } return(newMember); }
public PopulationMember mutate(PopulationMember member) { PopulationMember newMember = new PopulationMember(); newMember.parameters = member.parameters; int shiftAmount = _generator.next(1, 11) - 6; // Move up to 5 in either direction for (int i = 0; i < member.parameters.Length; i += 4) { if (_generator.next(0, MUTATION_PROBABILITY_INVERSE) == 0) { switch (_generator.next(0, 8)) { case 0: //right newMember.parameters [i] += shiftAmount; newMember.parameters [i + 2] += shiftAmount; break; case 1: //down newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 2: //left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 2] -= shiftAmount; break; case 3: //up newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; case 4: //up-right newMember.parameters [i] += shiftAmount; newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 2] += shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; case 5: //down-right newMember.parameters [i]++; newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 2] += shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 6: //down-left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 1] -= shiftAmount; newMember.parameters [i + 2] -= shiftAmount; newMember.parameters [i + 3] -= shiftAmount; break; case 7: //up-left newMember.parameters [i] -= shiftAmount; newMember.parameters [i + 1] += shiftAmount; newMember.parameters [i + 2] -= shiftAmount; newMember.parameters [i + 3] += shiftAmount; break; } } } return(newMember); }