private DNA[] CreateDNAs(int populationSize, int generation) { if (generation == 1) { return(new DNA[populationSize] .Select(t => new DNA((uint)CreatureCreator.NumGenesRequired)) .ToArray()); } var numFromHallOfFame = Mathf.RoundToInt(populationSize * FractionFromHallOfFame); // 1) select DNAs to breed new population from var parentDNAs = new DNA[populationSize]; // 1a) add some DNA from Hall of Fame int i; for (i = 0; i < HallOfFame.Count && i < numFromHallOfFame; i++) { parentDNAs[i] = HallOfFame.Values[i]; } // 1b) add some DNA from previous generation, based on fitness for (; i < populationSize; ++i) { parentDNAs[i] = PreviousGenerationDnasByFitness.GetRandomDistributedByKey( new DNA((uint)CreatureCreator.NumGenesRequired)).Item2; } FileLogger.Log(" parentDNAs: [{0}]", parentDNAs .Select(t => t.ToString()) .Aggregate((s, t) => string.Format("{0}, {1}", s, t))); // 2) breed new population var dnas = new DNA[populationSize]; // 2a) add some of the best DNA from the hall of fame directly for (i = 0; i < numFromHallOfFame; ++i) { dnas[i] = HallOfFame.Values[i]; } // 2b) breed the rest of the DNA from the prev. selected parent DNAs for (; i < populationSize; i += 2) { var parents = parentDNAs.GetRandom(2); var tuple = DNA.Breed(parents[0], parents[1]); dnas[i] = tuple.Item1; if (i + 1 < populationSize) { dnas[i + 1] = tuple.Item2; } } // 3) mutate new creatures dnas.ForEach(dna => { dna.Mutate(MutationMax); }); FileLogger.Log(" population: [{0}]", dnas .Select(t => t.ToString()) .Aggregate((s, t) => string.Format("{0}, {1}", s, t))); return(dnas); }