예제 #1
0
        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");
            }
        }
예제 #2
0
        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);
        }
예제 #4
0
        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);
        }
예제 #5
0
        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);
        }
예제 #6
0
        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);
        }
예제 #7
0
        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);
        }
예제 #8
0
        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);
        }
예제 #9
0
        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);
        }