/// <summary> /// Provides a brand-new individual to fill in a population. The default form /// simply calls clone(), creates a fitness, sets evaluated to false, and sets /// the species. If you need to make a more custom genotype (as is the case /// for GPSpecies, which requires a light rather than deep clone), /// you will need to override this method as you see fit. /// </summary> public virtual Individual NewIndividual(IEvolutionState state, int thread) { var newind = (Individual)I_Prototype.Clone(); // Set the fitness newind.Fitness = (Fitness)F_Prototype.Clone(); newind.Evaluated = false; // Set the species to me newind.Species = this; // ...and we're ready! return(newind); }
public virtual object Clone() { try { var myobj = (Species)(base.MemberwiseClone()); myobj.I_Prototype = (Individual)I_Prototype.Clone(); myobj.F_Prototype = (Fitness)F_Prototype.Clone(); myobj.Pipe_Prototype = (BreedingPipeline)Pipe_Prototype.Clone(); return(myobj); } catch (Exception) { throw new ApplicationException(); } // never happens }
/// <summary> /// Provides an individual read from a DataInput source, including /// the fitness. Doesn't /// close the DataInput. Sets evaluated to false and sets the species. /// If you need to make a more custom mechanism (as is the case /// for GPSpecies, which requires a light rather than deep clone), /// you will need to override this method as you see fit. /// </summary> public virtual Individual NewIndividual(IEvolutionState state, BinaryReader dataInput) { var newInd = (Individual)(I_Prototype.Clone()); // Set the fitness newInd.Fitness = (Fitness)(F_Prototype.Clone()); newInd.Evaluated = false; // for sanity's sake, though it's a useless line // Set the species to me newInd.Species = this; // load that sucker newInd.ReadIndividual(state, dataInput); // and we're ready! return(newInd); }
/// <summary> /// The default version of Setup(...) loads requested pipelines and calls Setup(...) on them and normalizes their probabilities. /// If your individual prototype might need to know special things about the species (like parameters stored in it), /// then when you override this Setup method, you'll need to set those parameters BEFORE you call super.Setup(...), /// because the Setup(...) code in Species sets up the prototype. /// </summary> /// <seealso cref="IPrototype.Setup(IEvolutionState, IParameter)" /> public virtual void Setup(IEvolutionState state, IParameter paramBase) { var def = DefaultBase; // load the breeding pipeline Pipe_Prototype = (BreedingSource)state.Parameters.GetInstanceForParameter(paramBase.Push(P_PIPE), def.Push(P_PIPE), typeof(BreedingSource)); Pipe_Prototype.Setup(state, paramBase.Push(P_PIPE)); // I promised over in BreedingSource.java that this method would get called. state.Output.ExitIfErrors(); // load our individual prototype I_Prototype = (Individual)(state.Parameters.GetInstanceForParameter(paramBase.Push(P_INDIVIDUAL), def.Push(P_INDIVIDUAL), typeof(Individual))); // set the species to me before setting up the individual, so they know who I am I_Prototype.Species = this; I_Prototype.Setup(state, paramBase.Push(P_INDIVIDUAL)); // load our fitness F_Prototype = (Fitness)state.Parameters.GetInstanceForParameter(paramBase.Push(P_FITNESS), def.Push(P_FITNESS), typeof(Fitness)); F_Prototype.Setup(state, paramBase.Push(P_FITNESS)); }
/** * Reverse of the original map() function, takes a GPIndividual and returns * a corresponding GEIndividual; The GPIndividual may contain more than one trees, * and such cases are handled accordingly, see the 3rd bullet below -- * * NOTE: * This reverse mapping is only valid for S-expression trees ; * * This procedure supports ERC for the current population (not for population * /subpopulation from other islands); However, that could be done by merging * all ERCBanks from all the sub-populations but that is not done yet ; * * Support for the ADF's are done as follows -- suppose in one GPIndividual, * there are N trees -- T1, T2, ,,, Tn and each of them follows n different * grammars G1, G2, ,,, Gn respectively; now if they are reverse-mapped to * int arrays, there will be n int arrays A1[], A2[], ,,, An[]; and suppose * the i-th tree Ti is reverse mapped to int array Ai[] and morevoer Ai[] is * the longest among all the arrays (Bj[]s); so Bi[] is sufficient to build * all ADF trees Tjs. */ public GEIndividual ReverseMap(IEvolutionState state, GPIndividual ind, int threadnum) { // create a dummy individual GEIndividual newind = (GEIndividual)I_Prototype.Clone(); // The longest int will be able to contain all ADF trees. int longestIntLength = -1; int[] longestInt = null; // Now go through all the ADF trees. for (int treeIndex = 0; treeIndex < ind.Trees.Length; treeIndex++) { // Flatten the Lisp tree ArrayList flatSexp = (ArrayList)FlattenSexp(state, threadnum, ind.Trees[treeIndex]); // Now convert the flatten list into an array of ints // no. of trees == no. of grammars int[] genomeVals = ParseSexp(flatSexp, GrammarParser[treeIndex]); // store the longest int array if (genomeVals.Length >= longestIntLength) { longestIntLength = genomeVals.Length; longestInt = new int[genomeVals.Length]; Array.Copy(genomeVals, 0, longestInt, 0, genomeVals.Length); } genomeVals = null; } // assign the longest int to the individual's genome newind.genome = longestInt; // update the GPIndividual's fitness information newind.Fitness = ind.Fitness; newind.Evaluated = false; // Set the species to me ? not sure. newind.Species = this; // return it return(newind); }
protected override void LoadParametersForGene(IEvolutionState state, int index, IParameter paramBase, IParameter def, String postfix) { base.LoadParametersForGene(state, index, paramBase, def, postfix); bool minValExists = state.Parameters.ParameterExists(paramBase.Push(P_MINGENE).Push(postfix), def.Push(P_MINGENE).Push(postfix)); bool maxValExists = state.Parameters.ParameterExists(paramBase.Push(P_MAXGENE).Push(postfix), def.Push(P_MAXGENE).Push(postfix)); if ((maxValExists && !minValExists)) { state.Output.Warning("Max Gene specified but not Min Gene", paramBase.Push(P_MINGENE).Push(postfix), def.Push(P_MINGENE).Push(postfix)); } if (minValExists && !maxValExists) { state.Output.Warning("Min Gene specified but not Max Gene", paramBase.Push(P_MAXGENE).Push(postfix), def.Push(P_MINGENE).Push(postfix)); } if (minValExists) { long minVal = state.Parameters.GetLongWithDefault(paramBase.Push(P_MINGENE).Push(postfix), def.Push(P_MINGENE).Push(postfix), 0); //check if the value is in range if (!InNumericalTypeRange(minVal)) { state.Output.Error("Min Gene Value out of range for data type " + I_Prototype.GetType().Name, paramBase.Push(P_MINGENE).Push(postfix), paramBase.Push(P_MINGENE).Push(postfix)); } else { MinGenes[index] = minVal; } if (DynamicInitialSize) { state.Output.WarnOnce("Using dynamic initial sizing, but per-gene or per-segment min-gene declarations. This is probably wrong. You probably want to use global min/max declarations.", paramBase.Push(P_MINGENE).Push(postfix), paramBase.Push(P_MINGENE).Push(postfix)); } } if (minValExists) { long maxVal = state.Parameters.GetLongWithDefault(paramBase.Push(P_MAXGENE).Push(postfix), def.Push(P_MAXGENE).Push(postfix), 0); //check if the value is in range if (!InNumericalTypeRange(maxVal)) { state.Output.Error("Max Gene Value out of range for data type " + I_Prototype.GetType().Name, paramBase.Push(P_MAXGENE).Push(postfix), paramBase.Push(P_MAXGENE).Push(postfix)); } else { MaxGenes[index] = maxVal; } if (DynamicInitialSize) { state.Output.WarnOnce("Using dynamic initial sizing, but per-gene or per-segment max-gene declarations. This is probably wrong. You probably want to use global min/max declarations.", paramBase.Push(P_MAXGENE).Push(postfix), paramBase.Push(P_MAXGENE).Push(postfix)); } } // MUTATION String mtype = state.Parameters.GetStringWithDefault(paramBase.Push(P_MUTATIONTYPE).Push(postfix), def.Push(P_MUTATIONTYPE).Push(postfix), null); int mutType = -1; if (mtype == null) { } // we're cool else if (mtype.Equals(V_RESET_MUTATION, StringComparison.InvariantCultureIgnoreCase)) { mutType = MutationType[index] = C_RESET_MUTATION; } else if (mtype.Equals(V_RANDOM_WALK_MUTATION, StringComparison.InvariantCultureIgnoreCase)) { mutType = MutationType[index] = C_RANDOM_WALK_MUTATION; state.Output.WarnOnce("Integer Random Walk Mutation used in IntegerVectorSpecies. Be advised that during initialization these genes will only be set to integer values."); } else { state.Output.Error("IntegerVectorSpecies given a bad mutation type: " + mtype, paramBase.Push(P_MUTATIONTYPE).Push(postfix), def.Push(P_MUTATIONTYPE).Push(postfix)); } if (mutType == C_RANDOM_WALK_MUTATION) { if (state.Parameters.ParameterExists(paramBase.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix), def.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix))) { RandomWalkProbability[index] = state.Parameters.GetDoubleWithMax(paramBase.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix), def.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix), 0.0, 1.0); if (RandomWalkProbability[index] <= 0) { state.Output.Error("If it's going to use random walk mutation as a per-gene or per-segment type, IntegerVectorSpecies must a random walk mutation probability between 0.0 and 1.0.", paramBase.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix), def.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix)); } } else { state.Output.Error("If IntegerVectorSpecies is going to use polynomial mutation as a per-gene or per-segment type, either the global or per-gene/per-segment random walk mutation probability must be defined.", paramBase.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix), def.Push(P_RANDOM_WALK_PROBABILITY).Push(postfix)); } if (state.Parameters.ParameterExists(paramBase.Push(P_MUTATION_BOUNDED).Push(postfix), def.Push(P_MUTATION_BOUNDED).Push(postfix))) { MutationIsBounded[index] = state.Parameters.GetBoolean(paramBase.Push(P_MUTATION_BOUNDED).Push(postfix), def.Push(P_MUTATION_BOUNDED).Push(postfix), true); } else if (!_mutationIsBoundedDefined) { state.Output.Fatal("If IntegerVectorSpecies is going to use gaussian, polynomial, or integer random walk mutation as a per-gene or per-segment type, the mutation bounding must be defined.", paramBase.Push(P_MUTATION_BOUNDED).Push(postfix), def.Push(P_MUTATION_BOUNDED).Push(postfix)); } } }
public override void Setup(IEvolutionState state, IParameter paramBase) { IParameter def = DefaultBase; SetupGenome(state, paramBase); // create the arrays MinGenes = new long[GenomeSize + 1]; MaxGenes = new long[GenomeSize + 1]; MutationType = Fill(new int[GenomeSize + 1], -1); MutationIsBounded = new bool[GenomeSize + 1]; RandomWalkProbability = new double[GenomeSize + 1]; // LOADING GLOBAL MIN/MAX GENES long minGene = state.Parameters.GetLongWithDefault(paramBase.Push(P_MINGENE), def.Push(P_MINGENE), 0); long maxGene = state.Parameters.GetLong(paramBase.Push(P_MAXGENE), def.Push(P_MAXGENE), minGene); if (maxGene < minGene) { state.Output.Fatal("IntegerVectorSpecies must have a default min-gene which is <= the default max-gene", paramBase.Push(P_MAXGENE), def.Push(P_MAXGENE)); } Fill(MinGenes, minGene); Fill(MaxGenes, maxGene); /// MUTATION String mtype = state.Parameters.GetStringWithDefault(paramBase.Push(P_MUTATIONTYPE), def.Push(P_MUTATIONTYPE), null); int mutType = C_RESET_MUTATION; if (mtype == null) { state.Output.Warning("No global mutation type given for IntegerVectorSpecies, assuming 'reset' mutation", paramBase.Push(P_MUTATIONTYPE), def.Push(P_MUTATIONTYPE)); } else if (mtype.Equals(V_RESET_MUTATION, StringComparison.InvariantCultureIgnoreCase)) { mutType = C_RESET_MUTATION; // redundant } else if (mtype.Equals(V_RANDOM_WALK_MUTATION, StringComparison.InvariantCultureIgnoreCase)) { mutType = C_RANDOM_WALK_MUTATION; } else { state.Output.Fatal("IntegerVectorSpecies given a bad mutation type: " + mtype, paramBase.Push(P_MUTATIONTYPE), def.Push(P_MUTATIONTYPE)); } Fill(MutationType, mutType); if (mutType == C_RANDOM_WALK_MUTATION) { double randWalkProb = state.Parameters.GetDoubleWithMax(paramBase.Push(P_RANDOM_WALK_PROBABILITY), def.Push(P_RANDOM_WALK_PROBABILITY), 0.0, 1.0); if (randWalkProb <= 0) { state.Output.Fatal("If it's going to use random walk mutation as its global mutation type, IntegerVectorSpecies must a random walk mutation probability between 0.0 and 1.0.", paramBase.Push(P_RANDOM_WALK_PROBABILITY), def.Push(P_RANDOM_WALK_PROBABILITY)); } Fill(RandomWalkProbability, randWalkProb); if (!state.Parameters.ParameterExists(paramBase.Push(P_MUTATION_BOUNDED), def.Push(P_MUTATION_BOUNDED))) { state.Output.Warning("IntegerVectorSpecies is using gaussian, polynomial, or integer randomwalk mutation as its global mutation type, but " + P_MUTATION_BOUNDED + " is not defined. Assuming 'true'"); } bool mutIsBounded = state.Parameters.GetBoolean(paramBase.Push(P_MUTATION_BOUNDED), def.Push(P_MUTATION_BOUNDED), true); Fill(MutationIsBounded, mutIsBounded); _mutationIsBoundedDefined = true; } base.Setup(state, paramBase); // VERIFY for (var x = 0; x < GenomeSize; x++) { if (MaxGenes[x] < MinGenes[x]) { state.Output.Fatal("IntegerVectorSpecies must have a min-gene[" + x + "] which is <= the max-gene[" + x + "]"); } // check to see if these longs are within the data type of the particular individual if (!InNumericalTypeRange(MinGenes[x])) { state.Output.Fatal("This IntegerVectorSpecies has a prototype of the kind: " + I_Prototype.GetType().FullName + ", but doesn't have a min-gene[" + x + "] value within the range of this prototype's genome's data types"); } if (!InNumericalTypeRange(MaxGenes[x])) { state.Output.Fatal("This IntegerVectorSpecies has a prototype of the kind: " + I_Prototype.GetType().FullName + ", but doesn't have a max-gene[" + x + "] value within the range of this prototype's genome's data types"); } } /* * //Debugging * for(int i = 0; i < minGenes.length; i++) * System.out.PrintLn("Min: " + minGenes[i] + ", Max: " + maxGenes[i]); */ }