コード例 #1
0
        AdjustFitnesses()
        {
            float total = 0;

            for (int i = 0; i < m_vecMembers.Count; i++)
            {
                CGenome member  = m_vecMembers[i];
                float   fitness = member.Fitness();

                if (m_iAge < _params.YoungAgeThreshold)
                {
                    fitness *= _params.YoungFitnessBonus;
                }
                else if (m_iAge > _params.OldAgeThreshold)
                {
                    fitness *= _params.OldAgePenalty;
                }

                total += fitness;

                // Calculation of fitness sharing
                float adjustedFitness = fitness / m_vecMembers.Count;

                member.SetAdjustedFitness(adjustedFitness);
            }
        }
コード例 #2
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        ResetAndKill()
        {
            m_dTotFitAdj = 0;
            m_dAvFitAdj  = 0;

            // Purge the species that doesn't improve
            for (int i = m_vecSpecies.Count - 1; i >= 0; i--)
            {
                CSpecies species = m_vecSpecies[i];
                species.Purge();

                if (species.GensNoImprovement() >
                    _params.NumGensAllowedNoImprovement &&
                    species.BestFitness() < m_dBestEverFitness)
                {
                    m_vecSpecies.RemoveAt(i);
                    Debug.Log("killed species " + species.ID());
                }
            }

            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome = m_Population[i];
                genome.DeletePhenotype();
            }
        }
コード例 #3
0
 CalculateSpawnAmount()
 {
     for (int i = 0; i < m_vecMembers.Count; i++)
     {
         CGenome member = m_vecMembers[i];
         m_dAmountToSpawn += member.AmountToSpawn();
     }
 }
コード例 #4
0
        CSpecies(CGenome leader, int speciesID)
        {
            m_vecMembers = new List <CGenome> ();

            m_iSpeciesID   = speciesID;
            m_dBestFitness = leader.Fitness();
            m_Leader       = leader;
            m_vecMembers.Add(leader);
        }
コード例 #5
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        Epoch(Dictionary <int, float> fitnessScores)
        {
            if (fitnessScores.Count != m_Population.Count)
            {
                Debug.LogError("scores and genomes mismatch error. (" + fitnessScores.Count + " / " + m_Population.Count + ")");
                return(null);
            }

            ResetAndKill();

            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome = m_Population[i];
                genome.SetFitness(fitnessScores[genome.ID()]);
            }

            SortAndRecord();
            SpeciateGenomes();
            CalculateSpawnLevels();

            Debug.Log("best fitness last gen: " + m_Population[0].Fitness());

            List <CGenome> newPopulation = new List <CGenome> ();

            int numSpawned = SpawnLeaders(newPopulation);

            for (int i = 0; i < m_vecSpecies.Count; i++)
            {
                CSpecies species = m_vecSpecies[i];
                numSpawned = SpawnOffspring(species, numSpawned, newPopulation);
            }

            /*
             * Tournament selection is used over the entire population if due
             * to a underflow of the species amount to spawn the offspring
             * doesn't fill the entire population additional children needs to
             * created.
             */
            if (numSpawned < _params.NumGenomesToSpawn)
            {
                int numMoreToSpawn = _params.NumGenomesToSpawn - numSpawned;

                while (numMoreToSpawn-- > 0)
                {
                    CGenome baby = new CGenome(TournamentSelection(m_PopSize / 5));
                    baby.SetID(++nextGenomeID);
                    newPopulation.Add(baby);
                }
            }

            m_Population = newPopulation;

            m_iGeneration++;

            return(CreatePhenotypes());
        }
コード例 #6
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        SpawnLeaders(List <CGenome> newPopulation)
        {
            for (int i = 0; i < m_vecSpecies.Count; i++)
            {
                CSpecies species = m_vecSpecies[i];
                CGenome  baby    = species.Leader();

                Debug.Log("spawning leader (" + baby.Fitness() + "): " + baby.ID() + " for " + species.ID());
                newPopulation.Add(baby);
            }

            return(newPopulation.Count);
        }
コード例 #7
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        CreatePhenotypes()
        {
            List <CNeuralNet> newPhenotypes = new List <CNeuralNet> ();

            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome = m_Population[i];

                int depth = CalculateNetDepth(genome);

                newPhenotypes.Add(genome.CreatePhenotype(depth));
            }

            return(newPhenotypes);
        }
コード例 #8
0
        AddMember(CGenome genome)
        {
            if (genome.Fitness() > m_dBestFitness)
            {
                m_dBestFitness          = genome.Fitness();
                m_iGensWithoutImproving = 0;
                m_Leader = genome;
            }

            m_vecMembers.Add(genome);

            /*
             * m_vecMembers.Sort(delegate (CGenome a, CGenome b) {
             *  return b.Fitness().CompareTo(a.Fitness());
             * });*/
        }
コード例 #9
0
 CGenome(CGenome original)
 {
     m_vecLinks   = new List <SLinkGene> ();
     m_vecNeurons = new List <SNeuronGene>();
     for (int i = 0; i < original.m_vecLinks.Count; i++)
     {
         m_vecLinks.Add(new SLinkGene(original.m_vecLinks[i]));
     }
     for (int i = 0; i < original.m_vecNeurons.Count; i++)
     {
         m_vecNeurons.Add(new SNeuronGene(original.m_vecNeurons[i]));
     }
     m_iNumInputs  = original.m_iNumInputs;
     m_iNumOutputs = original.m_iNumOutputs;
     m_GenomeID    = original.m_GenomeID;
 }
コード例 #10
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        CalculateNetDepth(CGenome genome)
        {
            int maxDepth = 0;

            for (int i = 0; i < genome.NumNeurons(); i++)
            {
                for (int j = 0; j < vecSplits.Count; j++)
                {
                    SplitDepth split = vecSplits[i];
                    if (genome.SplitY(i) == split.value &&
                        split.depth > maxDepth)
                    {
                        maxDepth = split.depth;
                    }
                }
            }

            return(maxDepth + 2);
        }
コード例 #11
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        TournamentSelection(int numSelections)
        {
            double  bestFitness = 0;
            CGenome best        = m_Population[0];

            for (int i = 0; i < numSelections; i++)
            {
                CGenome genome = m_Population[Random.Range(0, m_Population.Count)];

                if (genome.Fitness() > bestFitness)
                {
                    best = genome;

                    bestFitness = genome.Fitness();
                }
            }

            return(best);
        }
コード例 #12
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
 DetermineBestParent(CGenome mum, CGenome dad)
 {
     if (mum.Fitness() == dad.Fitness())
     {
         if (mum.NumGenes() == dad.NumGenes())
         {
             if (Random.value < 0.5)
             {
                 return(ParentType.Mum);
             }
             else
             {
                 return(ParentType.Dad);
             }
         }
         else
         {
             /*
              * Choose the parent with the fewest genes because
              * the fitness is the same.
              */
             if (mum.NumGenes() < dad.NumGenes())
             {
                 return(ParentType.Mum);
             }
             else
             {
                 return(ParentType.Dad);
             }
         }
     }
     else
     {
         if (mum.Fitness() > dad.Fitness())
         {
             return(ParentType.Mum);
         }
         else
         {
             return(ParentType.Dad);
         }
     }
 }
コード例 #13
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        MutateBaby(CGenome baby)
        {
            if (baby.NumNeurons() < _params.MaxPermittedNeurons)
            {
                baby.AddNeuron(_params.ChanceAddNode, innovation,
                               _params.NumTriesToFindOldLink);
            }

            baby.AddLink(_params.ChanceAddLink,
                         _params.ChanceAddRecurrentLink, innovation,
                         _params.NumTriesToFindLoopedLink,
                         _params.NumAddLinkAttempts);

            baby.MutateWeights(_params.MutationRate,
                               _params.ChanceWeightReplaced,
                               _params.MaxWeightPerturbation);

            baby.MutateActivationResponse(_params.ActivationMutationRate,
                                          _params.MaxActivationPerturbation);
        }
コード例 #14
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        CalculateSpawnLevels()
        {
            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome  = m_Population[i];
                float   toSpawn = 0;

                if (m_dAvFitAdj > 0)
                {
                    toSpawn = genome.GetAdjustedFitness() / m_dAvFitAdj;
                }

                genome.SetAmountToSpawn(toSpawn);
            }

            for (int i = 0; i < m_vecSpecies.Count; i++)
            {
                CSpecies species = m_vecSpecies[i];
                species.CalculateSpawnAmount();
            }
        }
コード例 #15
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        Cga(int inputs, int outputs)
        {
            m_Population = new List <CGenome> ();

            for (int i = 0; i < _params.NumGenomesToSpawn; i++)
            {
                m_Population.Add(new CGenome(nextGenomeID++, inputs, outputs));
            }
            m_PopSize = m_Population.Count;

            // Create simple genome used for innovations database
            CGenome genome = new CGenome(1, inputs, outputs);

            m_vecSpecies = new List <CSpecies> ();

            innovation = new CInnovation(genome.GetLinks(), genome.GetNeurons());

            vecSplits = new List <SplitDepth> ();

            // Create the network depth lookup table.
            Split(0, 1, 0);
        }
コード例 #16
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        Crossover(CGenome mum, CGenome dad)
        {
            ParentType best = DetermineBestParent(mum, dad);

            // The resulting offspring produced are stored in these lists.
            List <SNeuronGene> babyNeurons = new List <SNeuronGene>();
            List <SLinkGene>   babyGenes   = new List <SLinkGene>();
            List <int>         neuronIDs   = new List <int>();

            SelectGenesToBreed(mum, dad, best, babyGenes, neuronIDs);

            neuronIDs.Sort();

            // Create the new neurons using the neuron ids.
            for (int i = 0; i < neuronIDs.Count; i++)
            {
                int neuronID = neuronIDs[i];
                babyNeurons.Add(this.innovation.CreateNeuronByID(neuronID));
            }

            // Create the baby genome using the newly created neurons.
            return(new CGenome(nextGenomeID++, babyNeurons, babyGenes, mum.NumInputs(), mum.NumOutputs()));
        }
コード例 #17
0
        GetCompatibilityScore(CGenome other)
        {
            /*
             * Keep track of these numbers because genomes with different
             * topologies are unlikely to group together well. Therefore
             * the compatability score is based on how different the
             * topologies of the genomes are.
             */
            float numDisjointGenes = 0;
            float numExcessGenes   = 0;
            float numMatchedGenes  = 0;

            /*
             * The combined error/difference between the weights of the genomes.
             * A lower score means the behaviour is more probable to be
             * similar.
             */
            float weightDifference = 0;

            CalculateTopologyDifference(out numDisjointGenes, out numExcessGenes,
                                        out numMatchedGenes, out weightDifference,
                                        other);

            float longest = Mathf.Max(NumGenes(), other.NumGenes());

            /*
             * Coeffecients that are tweaked to influence the score
             * roughly the same amount.
             */
            const float coefDisjoint = 1.0f;
            const float coefExcess   = 1.0f;
            const float coefMatched  = 0.4f;

            return((coefExcess * numExcessGenes / longest) +
                   (coefDisjoint * numDisjointGenes / longest) +
                   (coefMatched * weightDifference / numMatchedGenes));
        }
コード例 #18
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        SpawnOffspring(CSpecies species, int numSpawned,
                       List <CGenome> newPopulation)
        {
            CGenome baby = null;

            /*
             * Prevent overflowing the total number of genomes spawned per population.
             */
            if (numSpawned < _params.NumGenomesToSpawn)
            {
                // Exclude the leader from numToSpawn.
                int numToSpawn = Mathf.RoundToInt(species.NumToSpawn()) - 1;

                numToSpawn = Mathf.Min(numToSpawn, _params.NumGenomesToSpawn - numSpawned);

                Debug.Log("spawning " + numToSpawn + " num indivudals for species " + species.ID() + ", best fitness: " + species.BestFitness());

                while (numToSpawn-- > 0)
                {
                    /*
                     * Unless we have >2 members in the species crossover
                     * can't be performed.
                     */
                    if (species.NumMembers() == 1)
                    {
                        baby = new CGenome(species.Spawn());
                    }
                    else
                    {
                        CGenome mum = species.Spawn();

                        if (Random.value < _params.CrossoverRate)
                        {
                            CGenome dad = species.Spawn();

                            int numAttempts = 5;

                            // try to select a genome which is not the same as mum
                            while (mum.ID() == dad.ID() && numAttempts-- > 0)
                            {
                                dad = species.Spawn();
                            }

                            if (mum.ID() != dad.ID())
                            {
                                baby = Crossover(mum, dad);
                            }
                            else
                            {
                                if (Random.value < 0.5f)
                                {
                                    baby = new CGenome(dad);
                                }
                                else
                                {
                                    baby = new CGenome(mum);
                                }
                            }
                        }
                        else
                        {
                            baby = new CGenome(mum);
                        }
                    }

                    if (baby == null)
                    {
                        continue;
                    }

                    baby.SetID(++nextGenomeID);

                    MutateBaby(baby);  //EDIT me

                    baby.SortGenes();

                    newPopulation.Add(baby);

                    if (numSpawned++ >= _params.NumGenomesToSpawn)
                    {
                        numToSpawn = 0;
                        break;
                    }
                }
            }

            return(numSpawned);
        }
コード例 #19
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        SpeciateGenomes()
        {
            bool addedToSpecies = false;

            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome = m_Population[i];

                float    bestCompatability = 1000;
                CSpecies bestSpecies       = null;

                for (int j = 0; j < m_vecSpecies.Count; j++)
                {
                    CSpecies species       = m_vecSpecies[j];
                    float    compatibility = genome.GetCompatibilityScore(species.Leader());

                    // if this individual is similar to this species leader add to species
                    if (compatibility < bestCompatability)
                    {
                        bestCompatability = compatibility;
                        bestSpecies       = species;
                    }
                }

                if (bestCompatability <= _params.CompatibilityThreshold)
                {
                    bestSpecies.AddMember(genome);

                    genome.SetSpecies(bestSpecies.ID());

                    addedToSpecies = true;
                }

                if (!addedToSpecies)
                {
                    // we have not found a compatible species so a new one will be created
                    m_vecSpecies.Add(new CSpecies(genome, nextSpeciesID++));
                }

                addedToSpecies = false;
            }

            /*
             * Adjust the fitness for all members of the every species to take
             * into account fitness sharing and age of species.
             */
            for (int i = 0; i < m_vecSpecies.Count; i++)
            {
                CSpecies species = m_vecSpecies[i];
                species.AdjustFitnesses();
            }

            /*
             * Calculate new adjusted total and average fitness for the population.
             */
            for (int i = 0; i < m_Population.Count; i++)
            {
                CGenome genome = m_Population[i];
                m_dTotFitAdj += genome.GetAdjustedFitness();
            }

            m_dAvFitAdj = m_dTotFitAdj / m_Population.Count;
        }
コード例 #20
0
ファイル: Cga.cs プロジェクト: itggot-linus-styren/NEATrobot
        SelectGenesToBreed(CGenome mum, CGenome dad, ParentType best,
                           List <SLinkGene> babyGenes,
                           List <int> neuronIDs)
        {
            List <SLinkGene> mumLinks = mum.GetLinks();
            List <SLinkGene> dadLinks = dad.GetLinks();

            using (IEnumerator <SLinkGene> mumEnumerator = mumLinks.GetEnumerator())
                using (IEnumerator <SLinkGene> dadEnumerator = dadLinks.GetEnumerator())
                {
                    bool      hasMumMore   = mumEnumerator.MoveNext();
                    bool      hasDadMore   = dadEnumerator.MoveNext();
                    SLinkGene selectedGene = mumEnumerator.Current;

                    while (hasMumMore || hasDadMore)
                    {
                        if (!hasMumMore && hasDadMore)
                        {
                            if (best == ParentType.Dad)
                            {
                                selectedGene = dadEnumerator.Current;
                            }
                            hasDadMore = dadEnumerator.MoveNext();
                        }
                        else if (!hasDadMore && hasMumMore)
                        {
                            if (best == ParentType.Mum)
                            {
                                selectedGene = mumEnumerator.Current;
                            }
                            hasMumMore = mumEnumerator.MoveNext();
                        }
                        else if (mumEnumerator.Current.InnovationID < dadEnumerator.Current.InnovationID)
                        {
                            if (best == ParentType.Mum)
                            {
                                selectedGene = mumEnumerator.Current;
                            }
                            hasMumMore = mumEnumerator.MoveNext();
                        }
                        else if (dadEnumerator.Current.InnovationID < mumEnumerator.Current.InnovationID)
                        {
                            if (best == ParentType.Dad)
                            {
                                selectedGene = dadEnumerator.Current;
                            }
                            hasDadMore = dadEnumerator.MoveNext();
                        }
                        else if (dadEnumerator.Current.InnovationID == mumEnumerator.Current.InnovationID)
                        {
                            if (Random.value < 0.5f)
                            {
                                selectedGene = mumEnumerator.Current;
                            }
                            else
                            {
                                selectedGene = dadEnumerator.Current;
                            }

                            hasMumMore = mumEnumerator.MoveNext();
                            hasDadMore = dadEnumerator.MoveNext();
                        }

                        if (babyGenes.Count == 0)
                        {
                            babyGenes.Add(new SLinkGene(selectedGene));
                        }
                        else
                        {
                            if (babyGenes[babyGenes.Count - 1].InnovationID !=
                                selectedGene.InnovationID)
                            {
                                babyGenes.Add(new SLinkGene(selectedGene));
                            }
                        }

                        AddNeuronID(selectedGene.FromNeuron, neuronIDs);
                        AddNeuronID(selectedGene.ToNeuron, neuronIDs);
                    }
                }
        }
コード例 #21
0
        CalculateTopologyDifference(out float numDisjoint, out float numExcess,
                                    out float numMatched, out float weightDiff,
                                    CGenome other)
        {
            numDisjoint = 0;
            numExcess   = 0;
            numMatched  = 0;
            weightDiff  = 0;

            /*
             * Current position of the gene in both genomes. We increment the
             * position as we traverse the topology of the genomes.
             */
            int g1 = 0;
            int g2 = 0;

            while (g1 < m_vecLinks.Count - 1 || g2 < other.m_vecLinks.Count - 1)
            {
                // more genes in genome1 than genome2
                if (g1 == m_vecLinks.Count - 1)
                {
                    g2++;
                    numExcess++;

                    continue;
                }

                // more gens in genome2 than genome1
                if (g2 == other.m_vecLinks.Count - 1)
                {
                    g1++;
                    numExcess++;

                    continue;
                }

                int id1 = m_vecLinks[g1].InnovationID;
                int id2 = other.m_vecLinks[g2].InnovationID;

                // compare innovation numbers
                if (id1 == id2)
                {
                    g1++;
                    g2++;
                    numMatched++;

                    weightDiff += Mathf.Abs((float)(m_vecLinks[g1].Weight - other.m_vecLinks[g2].Weight));
                }

                if (id1 < id2)
                {
                    g1++;
                    numDisjoint++;
                }

                if (id1 > id2)
                {
                    g2++;
                    numDisjoint++;
                }
            }
        }