Larger commit, adding IPOP-ES and RankMuCMA mutator. Revs. 130-174 from MK-branch should be merged with this.
This commit is contained in:
parent
c2a3f06498
commit
68241a0dc0
@ -3,19 +3,23 @@
|
||||
<title>Evolution Strategy - ES</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<h1 align="center">Evolution Strategy - ES</h1>
|
||||
<center>
|
||||
</center><br>
|
||||
An ES works on a population of real valued solutions
|
||||
by repeated use of evolutionary operators like reproduction,
|
||||
recombination and mutation (see pseudocode in figures.
|
||||
lambda offspring individuals are generated from mu parents
|
||||
by recombination and mutation. After evaluating the fitness of the lambda
|
||||
offspring individuals, mu individuals with the best fitness are
|
||||
selected by a comma-strategy to build the parent population for the next generation.
|
||||
On the other hand, a plus-strategy selects the best mu individuals
|
||||
from the aggregation of parents and offspring individuals.
|
||||
The properties of ES are given in the population sub frame.
|
||||
recombination and mutation.
|
||||
λ offspring individuals are generated from μ parents
|
||||
by recombination and mutation (with μ < λ).
|
||||
<br>
|
||||
After evaluating the fitness of the λ
|
||||
offspring individuals, the comma-strategy selects the μ individuals
|
||||
with the best fitness as parent population for the next generation.
|
||||
On the other hand, a plus-strategy selects the best μ individuals
|
||||
from the aggregation of parents and offspring individuals, so in this
|
||||
case the best individual is guaranteed to survive.
|
||||
In general, however, the comma-strategy is more robust and can easier
|
||||
escape from local optima, which is why it is usually the standard selection.
|
||||
<br>
|
||||
</body>
|
||||
</html>
|
30
resources/EvolutionStrategyIPOP.html
Normal file
30
resources/EvolutionStrategyIPOP.html
Normal file
@ -0,0 +1,30 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>Increasing Population Size ES - IPOP-ES</title>
|
||||
</head>
|
||||
<body>
|
||||
<h1 align="center">Increasing Population Size ES - IPOP-ES</h1>
|
||||
<center>
|
||||
</center><br>
|
||||
<p>
|
||||
This class implements the IPOP (increased population size) restart strategy ES, which increases
|
||||
the ES population size (i.e., lambda) after phases of stagnation and then restarts the optimization
|
||||
by reinitializing the individuals and operators.<br>
|
||||
Stagnation is for this implementation defined by a FitnessConvergenceTerminator instance
|
||||
which terminates if the absolute change in fitness is below a threshold (default 10e-12) for a
|
||||
certain number of generations (default: 10+floor(30*n/lambda) for problem dimension n).
|
||||
</p>
|
||||
<p>
|
||||
If the MutateESRankMuCMA mutation operator is employed, additional criteria are used for restarts,
|
||||
such as numeric conditions of the covariance matrix.
|
||||
Lambda is increased multiplicatively for every restart, and typical initial values are
|
||||
mu=5, lambda=10, incFact=2.
|
||||
The IPOP-CMA-ES won the CEC 2005 benchmark challenge.
|
||||
Refer to Auger&Hansen 05 for more details.
|
||||
</p>
|
||||
<br>
|
||||
A.Auger & N.Hansen. <i>A Restart CMA Evolution Strategy With Increasing Population Size</i>. CEC 2005.
|
||||
|
||||
|
||||
</body>
|
||||
</html>
|
33
resources/MutateESRankMuCMA.html
Normal file
33
resources/MutateESRankMuCMA.html
Normal file
@ -0,0 +1,33 @@
|
||||
<html>
|
||||
<head>
|
||||
<title>Covariance Matrix Adaptation with Rank-Mu-Update</title>
|
||||
</head>
|
||||
<body>
|
||||
<h1 align="center">Covariance Matrix Adaptation with rank-mu update after Hansen & Kern 2004</h1>
|
||||
|
||||
Implementing CMA ES with rank-mu-update and weighted recombination. This operator won the CEC 2005
|
||||
challenge employed with a restart scheme with increasing population size.
|
||||
Basically, in each generation the population is resampled around the weighted center of the
|
||||
last population using the adapted covariance matrix C. In contrast to earlier CMA versions,
|
||||
this implementation only holds one single covariance matrix for the whole population, making
|
||||
it much more memory efficient and useful for high dimensional problems as well.
|
||||
<br>
|
||||
While C is adapted based on a cumulated evolution path, the step size sigma is adapted based
|
||||
on path length control.
|
||||
Due to the repeated resampling starting from a single "center", the CMA version can
|
||||
be interpreted as a sophisticated local search, if the initial solution set is sampled
|
||||
close to an initial guess. In this case, a small initial sigma is favourable.
|
||||
<br>
|
||||
For multimodal problems, the initial population can be sampled randomly in the search space
|
||||
and the initial sigma must be rather high.
|
||||
To meet both conditions, the initial sigma may be set to half the average problem range
|
||||
or to the average distance in the initial population.
|
||||
|
||||
<br>
|
||||
<p>
|
||||
|
||||
* N.Hansen & S.Kern 2004: <i>Evaluating the CMA Evolution Strategy on Multimodal Test Functions.</i>
|
||||
Parallel Problem Solving from Nature 2004.
|
||||
|
||||
</body>
|
||||
</html>
|
@ -35,8 +35,8 @@ import eva2.server.go.individuals.GAIndividualDoubleData;
|
||||
import eva2.server.go.individuals.InterfaceDataTypeDouble;
|
||||
import eva2.server.go.operators.crossover.CrossoverGANPoint;
|
||||
import eva2.server.go.operators.mutation.InterfaceMutation;
|
||||
import eva2.server.go.operators.mutation.MutateESFixedStepSize;
|
||||
import eva2.server.go.operators.mutation.MutateESLocal;
|
||||
import eva2.server.go.operators.mutation.MutateESStandard;
|
||||
import eva2.server.go.operators.selection.SelectTournament;
|
||||
import eva2.server.go.operators.terminators.EvaluationTerminator;
|
||||
import eva2.server.go.populations.Population;
|
||||
@ -304,7 +304,7 @@ public class GOStandaloneVersion implements InterfaceGOStandalone, InterfacePopu
|
||||
this.m_OutputPath = "results/";
|
||||
// These are some tmp Variables
|
||||
InterfaceDataTypeDouble tmpIndy = new ESIndividualDoubleData();
|
||||
InterfaceMutation tmpMut = new MutateESStandard();
|
||||
InterfaceMutation tmpMut = new MutateESFixedStepSize();
|
||||
|
||||
switch (experimentType) {
|
||||
case 0 : {
|
||||
|
@ -2,6 +2,19 @@ package eva2.server.go.individuals;
|
||||
|
||||
import java.util.Comparator;
|
||||
|
||||
/**
|
||||
* Comparator implementation which compares two individuals based on their fitness.
|
||||
* The default version calls isDominatingDebConstraints() of the AbstractEAIndividual
|
||||
* class and assigns -1 if first is dominant, 1 if second is dominant, 0 if the two ind.s
|
||||
* are not comparable.
|
||||
* As an alternative, a data key String may be set which is then used to request a data
|
||||
* object from the individuals. The objects are interpreted as fitness vectors (double[]) and
|
||||
* the comparison is based on those. This may be used to access alternative (e.g. older or
|
||||
* best-so-far fitness values) for individual comparison.
|
||||
*
|
||||
* @author mkron
|
||||
*
|
||||
*/
|
||||
public class AbstractEAIndividualComparator implements Comparator<Object> {
|
||||
|
||||
// flag whether a data field should be used.
|
||||
@ -31,9 +44,21 @@ public class AbstractEAIndividualComparator implements Comparator<Object> {
|
||||
this.indyDataKey = indyDataKey;
|
||||
}
|
||||
|
||||
public AbstractEAIndividualComparator(AbstractEAIndividualComparator other) {
|
||||
indyDataKey = other.indyDataKey;
|
||||
}
|
||||
|
||||
public Object clone() {
|
||||
return new AbstractEAIndividualComparator(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Compare two individuals, return -1 if first is dominant, 1 if second is dominant, 0 if they
|
||||
* Compare two individuals, return -1 if the first is dominant, 1 if the second is dominant, 0 if they
|
||||
* are not comparable.
|
||||
*
|
||||
* @param o1 the first AbstractEAIndividual to compare
|
||||
* @param o2 the second AbstractEAIndividual to compare
|
||||
* @return -1 if the first is dominant, 1 if the second is dominant, else 0
|
||||
*/
|
||||
public int compare(Object o1, Object o2) {
|
||||
boolean o1domO2, o2domO1;
|
||||
|
@ -0,0 +1,15 @@
|
||||
package eva2.server.go.operators.mutation;
|
||||
|
||||
import eva2.server.go.populations.Population;
|
||||
|
||||
/**
|
||||
* An interface for a mutation operator which is updated on a generational basis, such as
|
||||
* the 1/5-success rule.
|
||||
*
|
||||
* @author mkron
|
||||
*
|
||||
*/
|
||||
public interface InterfaceMutationGenerational extends InterfaceMutation {
|
||||
public void adaptAfterSelection(Population oldGen, Population selected);
|
||||
public void adaptGenerational(Population selectedPop, Population parentPop, Population newPop, boolean updateSelected);
|
||||
}
|
@ -18,8 +18,8 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
protected double m_Tau1 = 0.15;
|
||||
protected double m_LowerLimitStepSize = 0.0000005;
|
||||
private static final long serialVersionUID = 1L;
|
||||
private double[] m_Sigmas;
|
||||
private double[] m_Alphas;
|
||||
private double[] m_Sigmas = null;
|
||||
private double[] m_Alphas = null;
|
||||
protected double m_Tau2 = 0.15;
|
||||
|
||||
public MutateESCorrolated() {
|
||||
@ -56,7 +56,7 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
return new MutateESCorrolated(this);
|
||||
}
|
||||
|
||||
/** This method allows you to evaluate wether two mutation operators
|
||||
/** This method allows you to evaluate whether two mutation operators
|
||||
* are actually the same.
|
||||
* @param mutator The other mutation operator
|
||||
*/
|
||||
@ -85,7 +85,19 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
* @param opt The optimization problem.
|
||||
*/
|
||||
public void init(AbstractEAIndividual individual, InterfaceOptimizationProblem opt) {
|
||||
|
||||
if (individual instanceof InterfaceESIndividual) {
|
||||
double[] x = ((InterfaceESIndividual)individual).getDGenotype();
|
||||
if (this.m_Sigmas == null) {
|
||||
// init the Sigmas
|
||||
this.m_Sigmas = new double[x.length];
|
||||
for (int i = 0; i < this.m_Sigmas.length; i++) this.m_Sigmas[i] = this.m_MutationStepSize;
|
||||
}
|
||||
if (this.m_Alphas == null) {
|
||||
// init the Alphas
|
||||
this.m_Alphas = new double[(x.length*(x.length-1))/2];
|
||||
for (int i = 0; i < this.m_Alphas.length; i++) this.m_Alphas[i] = 0.0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will mutate a given AbstractEAIndividual. If the individual
|
||||
@ -158,22 +170,12 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
double[][] range = ((InterfaceESIndividual)individual).getDoubleRange();
|
||||
double tmpR = RNG.gaussianDouble(1);
|
||||
|
||||
if (this.m_Sigmas == null) {
|
||||
// init the Sigmas
|
||||
this.m_Sigmas = new double[x.length];
|
||||
for (int i = 0; i < this.m_Sigmas.length; i++) this.m_Sigmas[i] = this.m_MutationStepSize;
|
||||
}
|
||||
//Mutate Sigmas
|
||||
for (int i = 0; i < x.length; i++) {
|
||||
this.m_Sigmas[i] = this.m_Sigmas[i] * Math.exp(this.m_Tau1 * tmpR + this.m_Tau2 * RNG.gaussianDouble(1));
|
||||
if (this.m_Sigmas[i] < this.m_LowerLimitStepSize) this.m_Sigmas[i] = this.m_LowerLimitStepSize;
|
||||
}
|
||||
|
||||
if (this.m_Alphas == null) {
|
||||
// init the Alphas
|
||||
this.m_Alphas = new double[(x.length*(x.length-1))/2];
|
||||
for (int i = 0; i < this.m_Alphas.length; i++) this.m_Alphas[i] = 0.0;
|
||||
}
|
||||
//Mutate Alphas
|
||||
for (int i = 0; i < this.m_Alphas.length; i++) {
|
||||
this.m_Alphas[i] = this.m_Alphas[i] + RNG.gaussianDouble(0.2);
|
||||
@ -230,7 +232,7 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
sum+=j-i; sum--;
|
||||
return this.m_Alphas[sum];
|
||||
}else{
|
||||
System.out.println("Falscher Zugriff auf Alphaliste!");
|
||||
System.err.println("Falscher Zugriff auf Alphaliste!");
|
||||
return 0.0;
|
||||
}
|
||||
}
|
||||
@ -240,7 +242,7 @@ public class MutateESCorrolated implements InterfaceMutation, java.io.Serializab
|
||||
* @return A descriptive string.
|
||||
*/
|
||||
public String getStringRepresentation() {
|
||||
return "ES local mutation";
|
||||
return "ES local correlated mutation";
|
||||
}
|
||||
|
||||
/**********************************************************************************************************************
|
||||
|
@ -160,6 +160,7 @@ public class MutateESCovarianceMatrixAdaption implements InterfaceMutation, java
|
||||
double pathLen = 0.0;
|
||||
for (int i = 0; i < this.m_D; i++)
|
||||
this.s_N[i] = (1.0 - this.m_c) * this.s_N[i] + this.m_c * this.cu * this.Bz[i];
|
||||
// System.out.println("C bef:\n" + m_C.toString());
|
||||
// ADAPT COVARIANCE
|
||||
for (int i = 0; i <this. m_D; i++) {
|
||||
for (int j = i; j < this.m_D; j++) {
|
||||
@ -168,6 +169,7 @@ public class MutateESCovarianceMatrixAdaption implements InterfaceMutation, java
|
||||
this.m_C.set(j, i, Cij);
|
||||
}
|
||||
}
|
||||
// System.out.println("C aft:\n" + m_C.toString());
|
||||
// ADAPT GLOBAL STEPSIZE
|
||||
for (int i = 0; i < this.m_D; i++) {
|
||||
Bz_d = 0.0;
|
||||
|
@ -14,8 +14,7 @@ import wsi.ra.math.RNG;
|
||||
* To change this template use File | Settings | File Templates.
|
||||
*/
|
||||
public class MutateESFixedStepSize implements InterfaceMutation, java.io.Serializable {
|
||||
|
||||
private double m_Sigma = 0.005;
|
||||
protected double m_Sigma = 0.005;
|
||||
|
||||
public MutateESFixedStepSize() {
|
||||
}
|
||||
|
@ -1,36 +1,43 @@
|
||||
package eva2.server.go.operators.mutation;
|
||||
|
||||
import wsi.ra.math.RNG;
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.individuals.InterfaceESIndividual;
|
||||
import eva2.server.go.populations.Population;
|
||||
import eva2.server.go.problems.InterfaceOptimizationProblem;
|
||||
import wsi.ra.math.RNG;
|
||||
import eva2.tools.Mathematics;
|
||||
|
||||
/**
|
||||
* Created by IntelliJ IDEA.
|
||||
* User: streiche
|
||||
* Date: 31.05.2005
|
||||
* Time: 14:22:13
|
||||
* To change this template use File | Settings | File Templates.
|
||||
* ES mutation with path length control. The step size (single sigma) is
|
||||
* adapted using the evolution path length by adapting the real path length
|
||||
* to the expected path length in for uncorrelated single steps.
|
||||
* See Hansen&Ostermeier 2001, Eqs. 16,17.
|
||||
*
|
||||
*/
|
||||
public class MutateESDerandomized implements InterfaceMutation, java.io.Serializable {
|
||||
public class MutateESPathLengthAdaption implements InterfaceMutation, java.io.Serializable {
|
||||
|
||||
private int m_D;
|
||||
private double[] m_Z;
|
||||
private int m_dim;
|
||||
private double[] m_randZ;
|
||||
private double[] m_Path;
|
||||
private double m_SigmaGlobal = 1.0;
|
||||
private double m_c;
|
||||
private boolean m_UsePath = true;
|
||||
private double dampening = 1;
|
||||
private double expectedPathLen = -1;
|
||||
private double m_cu;
|
||||
|
||||
public MutateESDerandomized() {
|
||||
public MutateESPathLengthAdaption() {
|
||||
|
||||
}
|
||||
public MutateESDerandomized(MutateESDerandomized mutator) {
|
||||
public MutateESPathLengthAdaption(MutateESPathLengthAdaption mutator) {
|
||||
this.m_UsePath = true;
|
||||
this.m_D = mutator.m_D;
|
||||
this.m_dim = mutator.m_dim;
|
||||
this.m_SigmaGlobal = mutator.m_SigmaGlobal;
|
||||
this.m_c = mutator.m_c;
|
||||
if (mutator.m_Z != null) this.m_Z = (double[]) mutator.m_Z.clone();
|
||||
this.dampening = mutator.dampening;
|
||||
this.expectedPathLen = mutator.expectedPathLen;
|
||||
this.m_cu = mutator.m_cu;
|
||||
if (mutator.m_randZ != null) this.m_randZ = (double[]) mutator.m_randZ.clone();
|
||||
if (mutator.m_Path != null) this.m_Path = (double[]) mutator.m_Path.clone();
|
||||
}
|
||||
|
||||
@ -38,7 +45,7 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
* @return The clone
|
||||
*/
|
||||
public Object clone() {
|
||||
return new MutateESDerandomized(this);
|
||||
return new MutateESPathLengthAdaption(this);
|
||||
}
|
||||
|
||||
/** This method allows you to evaluate wether two mutation operators
|
||||
@ -46,14 +53,14 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
* @param mutator The other mutation operator
|
||||
*/
|
||||
public boolean equals(Object mutator) {
|
||||
if (mutator instanceof MutateESDerandomized) {
|
||||
MutateESDerandomized mut = (MutateESDerandomized)mutator;
|
||||
if (mutator instanceof MutateESPathLengthAdaption) {
|
||||
MutateESPathLengthAdaption mut = (MutateESPathLengthAdaption)mutator;
|
||||
// i assume if the C Matrix is equal then the mutation operators are equal
|
||||
if (this.m_D != mut.m_D) return false;
|
||||
if (this.m_dim != mut.m_dim) return false;
|
||||
if (this.m_SigmaGlobal != mut.m_SigmaGlobal) return false;
|
||||
if (this.m_c != mut.m_c) return false;
|
||||
if ((this.m_Z != null) && (mut.m_Z != null))
|
||||
for (int i = 0; i < this.m_Z.length; i++) if (this.m_Z[i] != mut.m_Z[i]) return false;
|
||||
if ((this.m_randZ != null) && (mut.m_randZ != null))
|
||||
for (int i = 0; i < this.m_randZ.length; i++) if (this.m_randZ[i] != mut.m_randZ[i]) return false;
|
||||
if ((this.m_Path != null) && (mut.m_Path != null))
|
||||
for (int i = 0; i < this.m_Path.length; i++) if (this.m_Path[i] != mut.m_Path[i]) return false;
|
||||
return true;
|
||||
@ -69,13 +76,24 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
if (!(individual instanceof InterfaceESIndividual)) return;
|
||||
double[] x = ((InterfaceESIndividual)individual).getDGenotype();
|
||||
double[][] ranges = ((InterfaceESIndividual)individual).getDoubleRange();
|
||||
this.m_D = x.length;
|
||||
if (this.m_UsePath == true) this.m_c = Math.sqrt(1.0 / (double) this.m_D);
|
||||
this.m_dim = x.length;
|
||||
// if (this.m_UsePath) this.m_c = Math.sqrt(1.0 / (double) this.m_dim);
|
||||
|
||||
this.m_randZ = new double[this.m_dim];
|
||||
this.m_Path = new double[this.m_dim];
|
||||
for (int i = 0; i < this.m_dim; i++) {
|
||||
this.m_randZ[i] = RNG.gaussianDouble(1.0);
|
||||
// this.m_Path[i]=1;
|
||||
}
|
||||
|
||||
if (this.m_UsePath) this.m_c = 4./(m_dim+4);
|
||||
else this.m_c = 1.0;
|
||||
this.m_Z = new double[this.m_D];
|
||||
this.m_Path = new double[this.m_D];
|
||||
for (int i = 0; i < this.m_D; i++) this.m_Z[i] = RNG.gaussianDouble(1.0);
|
||||
evaluateNewObjectX(x, ranges);
|
||||
|
||||
expectedPathLen = Math.sqrt(m_dim)*(1-(1./(4*m_dim))+(1./(21*m_dim*m_dim)));
|
||||
dampening = (1./m_c)+1;
|
||||
m_cu = Math.sqrt(m_c*(2.0-m_c));
|
||||
|
||||
mutateX(x, ranges, true);
|
||||
}
|
||||
|
||||
/** This method will mutate a given AbstractEAIndividual. If the individual
|
||||
@ -87,19 +105,30 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
if (individual instanceof InterfaceESIndividual) {
|
||||
double[] x = ((InterfaceESIndividual)individual).getDGenotype();
|
||||
double[][] ranges = ((InterfaceESIndividual)individual).getDoubleRange();
|
||||
this.adaptStrategy();
|
||||
for (int i = 0; i < m_D; i++) m_Z[i] = RNG.gaussianDouble(1.0);
|
||||
this.evaluateNewObjectX(x, ranges);
|
||||
for (int i = 0; i < x.length; i++) {
|
||||
if (x[i] < ranges[i][0]) x[i] = ranges[i][0];
|
||||
if (x[i] > ranges[i][1]) x[i] = ranges[i][1];
|
||||
}
|
||||
|
||||
this.adaptStrategy(); // this updates the path using the old step and adapts sigma
|
||||
|
||||
this.calculateNewStep();
|
||||
|
||||
this.mutateX(x, ranges, true); // this performs new mutation
|
||||
|
||||
((InterfaceESIndividual)individual).SetDGenotype(x);
|
||||
}
|
||||
//System.out.println("After Mutate: " +((GAIndividual)individual).getSolutionRepresentationFor());
|
||||
}
|
||||
|
||||
private void checkRange(double[] x, double[][] ranges) {
|
||||
for (int i = 0; i < x.length; i++) {
|
||||
if (x[i] < ranges[i][0]) x[i] = ranges[i][0];
|
||||
if (x[i] > ranges[i][1]) x[i] = ranges[i][1];
|
||||
}
|
||||
}
|
||||
|
||||
/** This method allows you to perform either crossover on the strategy parameters
|
||||
private void calculateNewStep() {
|
||||
for (int i = 0; i < m_dim; i++) m_randZ[i] = RNG.gaussianDouble(1.0);
|
||||
}
|
||||
|
||||
/** This method allows you to perform either crossover on the strategy parameters
|
||||
* or to deal in some other way with the crossover event.
|
||||
* @param indy1 The original mother
|
||||
* @param partners The original partners
|
||||
@ -109,21 +138,23 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
}
|
||||
|
||||
private void adaptStrategy() {
|
||||
double length_of_Z = 0;
|
||||
for (int i = 0; i < m_D; i++) {
|
||||
m_Path [i] = (1.0 -m_c) * m_Path[i] + Math.sqrt(m_c*(2.0-m_c))*m_Z[i];
|
||||
length_of_Z = length_of_Z + m_Path[i] * m_Path[i];
|
||||
// remember the path taken. m_randZ is at this time the last step before selection.
|
||||
for (int i = 0; i < m_dim; i++) {
|
||||
m_Path [i] = (1.0 -m_c) * m_Path[i] + m_cu*m_randZ[i];
|
||||
}
|
||||
length_of_Z = Math.sqrt(length_of_Z);
|
||||
double E_of_length_of_Z = Math.sqrt(((double)m_D)+0.5);
|
||||
double kappa_d = ((double)m_D)/4.0+1.0;
|
||||
double Exponent = (length_of_Z - E_of_length_of_Z)/(kappa_d*E_of_length_of_Z);
|
||||
m_SigmaGlobal = m_SigmaGlobal * Math.exp(Exponent);
|
||||
double pathLen = Mathematics.norm(m_Path);
|
||||
|
||||
// double expectedPathLen = Math.sqrt(((double)m_dim)+0.5);
|
||||
// double kappa_d = ((double)m_dim)/4.0+1.0;
|
||||
|
||||
double exp = (pathLen - expectedPathLen)/(dampening*expectedPathLen);
|
||||
m_SigmaGlobal = m_SigmaGlobal * Math.exp(exp);
|
||||
}
|
||||
|
||||
private void evaluateNewObjectX(double[] x,double[][] range) {
|
||||
private void mutateX(double[] x,double[][] range, boolean checkRange) {
|
||||
for (int i = 0; i < x.length; i++)
|
||||
x[i] = x[i] + m_SigmaGlobal * m_Z[i];
|
||||
x[i] = x[i] + m_SigmaGlobal * m_randZ[i];
|
||||
if (checkRange) checkRange(x, range);
|
||||
}
|
||||
|
||||
/** This method allows you to get a string representation of the mutation
|
||||
@ -131,7 +162,7 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
* @return A descriptive string.
|
||||
*/
|
||||
public String getStringRepresentation() {
|
||||
return "CMA mutation";
|
||||
return "Mutation/Path-Length-Control";
|
||||
}
|
||||
/**********************************************************************************************************************
|
||||
* These are for GUI
|
||||
@ -141,27 +172,27 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
* @return The name.
|
||||
*/
|
||||
public String getName() {
|
||||
return "CMA mutation";
|
||||
return "Mutation/Path-Length-Control";
|
||||
}
|
||||
/** This method returns a global info string
|
||||
* @return description
|
||||
*/
|
||||
public String globalInfo() {
|
||||
return "This is the most sophisticated CMA mutation.";
|
||||
return "The single step size is controlled using the evolution path.";
|
||||
}
|
||||
|
||||
/** Use only positive numbers this limits the freedom of effect.
|
||||
* @param bit The new representation for the inner constants.
|
||||
*/
|
||||
public void setUsePath(boolean bit) {
|
||||
this.m_UsePath = bit;
|
||||
}
|
||||
public boolean getUsePath() {
|
||||
return this.m_UsePath;
|
||||
}
|
||||
public String usePathTipText() {
|
||||
return "Use path.";
|
||||
}
|
||||
// /** Use only positive numbers this limits the freedom of effect.
|
||||
// * @param bit The new representation for the inner constants.
|
||||
// */
|
||||
// public void setUsePath(boolean bit) {
|
||||
// this.m_UsePath = bit;
|
||||
// }
|
||||
// public boolean getUsePath() {
|
||||
// return this.m_UsePath;
|
||||
// }
|
||||
// public String usePathTipText() {
|
||||
// return "Use path.";
|
||||
// }
|
||||
|
||||
/** This method allows you to set the initial sigma value.
|
||||
* @param d The initial sigma value.
|
||||
@ -173,6 +204,6 @@ public class MutateESDerandomized implements InterfaceMutation, java.io.Serializ
|
||||
return this.m_SigmaGlobal;
|
||||
}
|
||||
public String initSigmaGlobalTipText() {
|
||||
return "Set the initial global sigma value.";
|
||||
return "Set the initial global step size.";
|
||||
}
|
||||
}
|
648
src/eva2/server/go/operators/mutation/MutateESRankMuCMA.java
Normal file
648
src/eva2/server/go/operators/mutation/MutateESRankMuCMA.java
Normal file
@ -0,0 +1,648 @@
|
||||
package eva2.server.go.operators.mutation;
|
||||
|
||||
import java.io.Serializable;
|
||||
import java.util.Arrays;
|
||||
|
||||
import wsi.ra.math.RNG;
|
||||
import wsi.ra.math.Jama.EigenvalueDecomposition;
|
||||
import wsi.ra.math.Jama.Matrix;
|
||||
import eva2.gui.BeanInspector;
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.individuals.InterfaceDataTypeDouble;
|
||||
import eva2.server.go.populations.Population;
|
||||
import eva2.server.go.problems.InterfaceOptimizationProblem;
|
||||
import eva2.tools.EVAERROR;
|
||||
import eva2.tools.Mathematics;
|
||||
import eva2.tools.Pair;
|
||||
|
||||
|
||||
/**
|
||||
* Implementing CMA ES with rank-mu-update and weighted recombination. This is partly based on the
|
||||
* java implementation provided on http://www.bionik.tu-berlin.de/user/niko/cmaes_inmatlab.html.
|
||||
*
|
||||
* N.Hansen & S.Kern 2004: Evaluating the CMA Evolution Strategy on Multimodal Test Functions.
|
||||
* Parallel Problem Solving from Nature 2004.
|
||||
*
|
||||
* @author mkron
|
||||
*
|
||||
*/
|
||||
public class MutateESRankMuCMA implements InterfaceMutationGenerational, Serializable {
|
||||
int dim;
|
||||
private double c_c, expRandStepLen;
|
||||
private double[] z, zCor;
|
||||
|
||||
private InitialSigmaEnum initialSig = InitialSigmaEnum.avgInitialDistance;
|
||||
private static double firstSigma = -1.;
|
||||
private static double sigma;
|
||||
private static double d_sig, c_sig;
|
||||
private static double[] meanX, pathC, pathS, eigenvalues;
|
||||
private static double[] weights = null;
|
||||
private static double[][] range = null;
|
||||
private static Matrix mC;
|
||||
private static Matrix mB;
|
||||
// private static double[] mBD;
|
||||
private static boolean firstAdaptionDone = false;
|
||||
private static boolean TRACE_1 = false;
|
||||
private static boolean TRACE_2 = false;
|
||||
private static boolean TRACE_TEST = false;
|
||||
// private Matrix BD;
|
||||
|
||||
public MutateESRankMuCMA() {
|
||||
firstAdaptionDone = false;
|
||||
}
|
||||
|
||||
public MutateESRankMuCMA(MutateESRankMuCMA mutator) {
|
||||
this.c_c = mutator.c_c;
|
||||
// this.c_sig = mutator.c_sig;
|
||||
// this.c_u_sig = mutator.c_u_sig;
|
||||
// this.d_sig = mutator.d_sig;
|
||||
this.expRandStepLen = mutator.expRandStepLen;
|
||||
this.dim = mutator.dim;
|
||||
this.initialSig = mutator.initialSig;
|
||||
|
||||
// if (mutator.meanX != null) this.meanX = (double[]) mutator.meanX.clone();
|
||||
// if (mutator.pathC != null) this.pathC = (double[]) mutator.pathC.clone();
|
||||
// if (mutator.pathS != null) this.pathS = (double[]) mutator.pathS.clone();
|
||||
if (mutator.z != null) this.z = (double[]) mutator.z.clone();
|
||||
if (mutator.zCor != null) this.zCor = (double[]) mutator.zCor.clone();
|
||||
// if (mutator.eigenvalues != null) this.eigenvalues = (double[]) mutator.eigenvalues.clone();
|
||||
// if (mutator.mC != null) this.mC = (Matrix) mutator.mC.clone();
|
||||
// if (mutator.mB != null) this.mB = (Matrix) mutator.mB.clone();
|
||||
}
|
||||
|
||||
public Object clone() {
|
||||
// if (TRACE) System.out.println("WCMA clone");
|
||||
return new MutateESRankMuCMA(this);
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieve the initial sigma for the given population and the user defined method.
|
||||
* @param initGen
|
||||
* @return
|
||||
*/
|
||||
private double getInitSigma(Population initGen) {
|
||||
switch (initialSig) {
|
||||
case avgInitialDistance: return initGen.getPopulationMeasures()[0];
|
||||
case halfRange: return getAvgRange()/2.;
|
||||
default: return 0.2;
|
||||
}
|
||||
}
|
||||
|
||||
public void adaptAfterSelection(Population oldGen, Population selectedP) {
|
||||
Population selectedSorted = selectedP.getSortedBestFirst();
|
||||
|
||||
int mu,lambda;
|
||||
mu = selectedP.size();
|
||||
lambda = oldGen.size();
|
||||
if (mu>= lambda) {
|
||||
EVAERROR.errorMsgOnce("Warning: invalid mu/lambda ratio! Setting mu to lambda/2.");
|
||||
mu = lambda/2;
|
||||
}
|
||||
if (!firstAdaptionDone) {
|
||||
initWeights(mu, lambda);
|
||||
double muEff = getMuEff(mu);
|
||||
c_sig = (muEff+2)/(muEff+dim+3);
|
||||
// c_u_sig = Math.sqrt(c_sig * (2.-c_sig));
|
||||
d_sig = c_sig+1+2*Math.max(0, Math.sqrt((muEff-1)/(dim+1)) - 1);
|
||||
sigma = getInitSigma(oldGen);
|
||||
firstSigma = sigma;
|
||||
meanX = oldGen.getCenter(); // this might be ok?
|
||||
}
|
||||
|
||||
int generation = oldGen.getGeneration();
|
||||
|
||||
if (TRACE_1) {
|
||||
System.out.println("WCMA adaptGenerational");
|
||||
// System.out.println("newPop measures: " + BeanInspector.toString(newPop.getPopulationMeasures()));
|
||||
System.out.println("mu_eff: " + getMuEff(mu));
|
||||
System.out.println("meanX: " + BeanInspector.toString(meanX));
|
||||
System.out.println("pathC: " + BeanInspector.toString(pathC));
|
||||
System.out.println("pathS: " + BeanInspector.toString(pathS));
|
||||
}
|
||||
|
||||
double[] newMeanX = calcMeanX(selectedSorted);
|
||||
if (TRACE_1) System.out.println("newMeanX: " + BeanInspector.toString(newMeanX));
|
||||
|
||||
double[] BDz = new double[dim];
|
||||
for (int i=0; i<dim; i++) { /* calculate xmean and BDz~N(0,C) */
|
||||
// Eq. 4 from HK04, most right term
|
||||
BDz[i] = Math.sqrt(getMuEff(mu)) * (newMeanX[i] - meanX[i]) / getSigma(i);
|
||||
}
|
||||
// if (TRACE_2) System.out.println("BDz is " + BeanInspector.toString(BDz));
|
||||
|
||||
double[] newPathS = pathS.clone();
|
||||
double[] newPathC = pathC.clone();
|
||||
|
||||
double[] zVect = new double[dim];
|
||||
/* calculate z := D^(-1) * B^(-1) * BDz into artmp, we could have stored z instead */
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
double sum=0.;
|
||||
for (int j = 0; j < dim; ++j) {
|
||||
sum += mB.get(j,i) * BDz[j]; // times B transposed, (Eq 4) in HK04
|
||||
}
|
||||
zVect[i] = sum / Math.sqrt(eigenvalues[i]);
|
||||
}
|
||||
|
||||
/* cumulation for sigma (ps) using B*z */
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
double sum = 0.;
|
||||
for (int j = 0; j < dim; ++j) sum += mB.get(i,j) * zVect[j];
|
||||
newPathS[i] = (1. - getCs()) * pathS[i]
|
||||
+ Math.sqrt(getCs() * (2. - getCs())) * sum;
|
||||
}
|
||||
// System.out.println("pathS diff: " + BeanInspector.toString(Mathematics.vvSub(newPathS, pathS)));
|
||||
// System.out.println("newPathS is " + BeanInspector.toString(newPathS));
|
||||
|
||||
double psNorm = Mathematics.norm(newPathS);
|
||||
|
||||
double hsig = 0;
|
||||
if (psNorm / Math.sqrt(1. - Math.pow(1. - getCs(), 2. * generation))
|
||||
/ expRandStepLen < 1.4 + 2. / (dim + 1.)) {
|
||||
hsig = 1;
|
||||
}
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
newPathC[i] = (1. - getCc()) * pathC[i] + hsig
|
||||
* Math.sqrt(getCc() * (2. - getCc())) * BDz[i];
|
||||
}
|
||||
|
||||
// TODO missing: "remove momentum in ps"
|
||||
|
||||
if (TRACE_1) {
|
||||
System.out.println("newPathC: " + BeanInspector.toString(newPathC));
|
||||
System.out.println("newPathS: " + BeanInspector.toString(newPathS));
|
||||
}
|
||||
|
||||
if (TRACE_1) System.out.println("Bef: C is \n" + mC.toString());
|
||||
if (meanX == null) meanX = newMeanX;
|
||||
|
||||
updateCov(newPathC, newMeanX, hsig, mu, selectedSorted);
|
||||
updateBD();
|
||||
|
||||
if (TRACE_2) System.out.println("Aft: C is \n" + mC.toString());
|
||||
|
||||
/* update of sigma */
|
||||
sigma *= Math.exp(((psNorm / expRandStepLen) - 1) * getCs()
|
||||
/ getDamps());
|
||||
if (Double.isInfinite(sigma) || Double.isNaN(sigma)) {
|
||||
System.err.println("Error, unstable sigma!");
|
||||
}
|
||||
testAndCorrectNumerics(generation, selectedSorted);
|
||||
|
||||
// System.out.println("sigma=" + sigma + " psLen=" + (psNorm) + " chiN="+expRandStepLen + " cs="+getCs()+ " damps="+getDamps() + " diag " + BeanInspector.toString(eigenvalues));
|
||||
if (TRACE_1) {
|
||||
System.out.print("psLen=" + (psNorm) + " ");
|
||||
outputParams(mu);
|
||||
}
|
||||
|
||||
// take over data
|
||||
meanX = newMeanX;
|
||||
pathC = newPathC;
|
||||
pathS = newPathS;
|
||||
firstAdaptionDone = true;
|
||||
// if (TRACE_2) System.out.println("sampling around " + BeanInspector.toString(meanX));
|
||||
}
|
||||
|
||||
/**
|
||||
* Expects newPop to have correct number of generations set.
|
||||
*/
|
||||
public void adaptGenerational(Population oldPop, Population selectedPop,
|
||||
Population newPop, boolean updateSelected) {
|
||||
// nothing to do?
|
||||
}
|
||||
|
||||
/**
|
||||
* Requires selected population to be sorted by fitness.
|
||||
*
|
||||
* @param iterations
|
||||
* @param selected
|
||||
*/
|
||||
void testAndCorrectNumerics(int iterations, Population selected) { // not much left here
|
||||
/* Flat Fitness, Test if function values are identical */
|
||||
if (iterations > 1) {
|
||||
// selected pop is sorted
|
||||
if (nearlySame(selected.getEAIndividual(0).getFitness(),selected.getEAIndividual(selected.size()-1).getFitness())) {
|
||||
if (TRACE_1) System.err.println("flat fitness landscape, consider reformulation of fitness, step-size increased");
|
||||
sigma *= Math.exp(0.2+getCs()/getDamps());
|
||||
// sigma=0.1;
|
||||
}
|
||||
}
|
||||
/* Align (renormalize) scale C (and consequently sigma) */
|
||||
/* e.g. for infinite stationary state simulations (noise
|
||||
* handling needs to be introduced for that) */
|
||||
double fac = 1.;
|
||||
double minEig = 1e-12;
|
||||
double maxEig = 1e8;
|
||||
if (Mathematics.max(eigenvalues) < minEig)
|
||||
fac = 1./Math.sqrt(Mathematics.max(eigenvalues));
|
||||
else if (Mathematics.min(eigenvalues) > maxEig)
|
||||
fac = 1./Math.sqrt(Mathematics.min(eigenvalues));
|
||||
|
||||
if (fac != 1.) {
|
||||
System.err.println("Scaling by " + fac);
|
||||
sigma /= fac;
|
||||
for(int i = 0; i < dim; ++i) {
|
||||
pathC[i] *= fac;
|
||||
eigenvalues[i] *= fac*fac;
|
||||
for (int j = 0; j <= i; ++j) {
|
||||
mC.set(i, j, mC.get(i,j)*fac*fac);
|
||||
if (i!=j) mC.set(j, i, mC.get(i,j));
|
||||
}
|
||||
}
|
||||
}
|
||||
} // Test...
|
||||
|
||||
private boolean nearlySame(double[] bestFitness, double[] worstFitness) {
|
||||
double epsilon = 1e-14;
|
||||
for (int i=0; i<bestFitness.length; i++) if (Math.abs(bestFitness[i]-worstFitness[i])>epsilon) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the range scaled sigma parameter for dimension i.
|
||||
*
|
||||
* @param i
|
||||
* @return
|
||||
*/
|
||||
private double getSigma(int i) {
|
||||
return sigma;
|
||||
}
|
||||
|
||||
private double getDamps() {
|
||||
return d_sig;
|
||||
}
|
||||
|
||||
private double getCc() {
|
||||
return c_c;
|
||||
}
|
||||
|
||||
private double getCs() {
|
||||
return c_sig;
|
||||
}
|
||||
|
||||
private double calcExpRandStepLen() {
|
||||
// scale by avg range?
|
||||
return Math.sqrt(dim)*(1.-(1./(4*dim))+(1./(21*dim*dim)));
|
||||
}
|
||||
|
||||
private double getAvgRange() {
|
||||
double sum = 0.;
|
||||
for (int i=0; i<dim; i++) sum+=(range[i][1]-range[i][0]);
|
||||
return sum/dim;
|
||||
}
|
||||
|
||||
/* update C */
|
||||
private void updateCov(double[] newPathC, double[] newMeanX, double hsig, int mu, Population selected) {
|
||||
double newVal = 0;
|
||||
if (getCCov(mu) > 0) {
|
||||
/* (only upper triangle!) */
|
||||
/* update covariance matrix */
|
||||
//System.out.println("CCov " + getCCov(selected) + " Cc " + getCc() + " muCov " + getMuCov(selected));
|
||||
for (int i = 0; i < dim; ++i)
|
||||
for (int j = 0; j <= i; ++j) {
|
||||
// oldVal = mC.get(i,j);
|
||||
newVal = (1 - getCCov(mu)) * mC.get(i,j)
|
||||
+ getCCov(mu)
|
||||
* (1. / getMuCov(mu))
|
||||
* (newPathC[i] * newPathC[j] + (1 - hsig) * getCc()
|
||||
* (2. - getCc()) * mC.get(i,j));
|
||||
mC.set(i,j,newVal);
|
||||
for (int k = 0; k < mu; ++k) { /*
|
||||
* additional rank mu
|
||||
* update
|
||||
*/
|
||||
double[] x_k = ((InterfaceDataTypeDouble)selected.getEAIndividual(k)).getDoubleData();
|
||||
newVal = mC.get(i,j)+ getCCov(mu) * (1 - 1. / getMuCov(mu))
|
||||
* getWeight(k) * (x_k[i] - meanX[i])
|
||||
* (x_k[j] - meanX[j]) / (getSigma(i) * getSigma(j)); // TODO right sigmas?
|
||||
mC.set(i,j, newVal);
|
||||
}
|
||||
}
|
||||
// fill rest of C
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
for (int j = i+1; j < dim; ++j) {
|
||||
|
||||
mC.set(i, j, mC.get(j,i));
|
||||
}
|
||||
|
||||
}
|
||||
if (mC.get(0,1) != mC.get(1,0)) {
|
||||
System.err.println("WARNING");
|
||||
}
|
||||
// maxsqrtdiagC = Math.sqrt(math.max(math.diag(C)));
|
||||
// minsqrtdiagC = Math.sqrt(math.min(math.diag(C)));
|
||||
} // update of C
|
||||
|
||||
}
|
||||
|
||||
private double getMuCov(int mu) {
|
||||
// default parameter value ( HK03, sec. 2)
|
||||
return getMuEff(mu);
|
||||
}
|
||||
|
||||
private double getCCov(int mu) {
|
||||
// ( HK03, sec. 2)
|
||||
//return Math.min(1., 2*getMuEff(selected)/(dim*dim));
|
||||
double ccov = (2./(getMuCov(mu)*Math.pow(dim+Math.sqrt(2.), 2)))+(1.-(1./getMuCov(mu)))*Math.min(1., (2*getMuEff(mu)-1.)/(dim*dim+2*dim+4+getMuEff(mu)));
|
||||
return ccov;
|
||||
}
|
||||
|
||||
private double getMuEff(int mu) {
|
||||
double res = 0, u;
|
||||
for (int i=0; i<mu;i++) {
|
||||
u = getWeight(i);
|
||||
res += u*u;
|
||||
}
|
||||
return 1./res;
|
||||
}
|
||||
|
||||
private void outputParams(int mu) {
|
||||
System.out.println("sigma=" + sigma + " chiN="+expRandStepLen + " cs="+getCs()+ " damps="+getDamps() + " Cc=" + getCc() + " Ccov=" + getCCov(mu) + " mueff=" + getMuEff(mu) + " mucov="+getMuCov(mu));
|
||||
}
|
||||
|
||||
private void updateBD() {
|
||||
// C=triu(C)+transpose(triu(C,1)); % enforce symmetry
|
||||
// [B,D] = eig(C);
|
||||
// % limit condition of C to 1e14 + 1
|
||||
// if max(diag(D)) > 1e14*min(diag(D))
|
||||
// tmp = max(diag(D))/1e14 - min(diag(D));
|
||||
// C = C + tmp*eye(N);
|
||||
// D = D + tmp*eye(N);
|
||||
// end
|
||||
// D = diag(sqrt(diag(D))); % D contains standard deviations now
|
||||
// BD = B*D; % for speed up only
|
||||
////////////////////////////////////////////7
|
||||
mC = (mC.plus(mC.transpose()).times(0.5)); // MAKE C SYMMETRIC
|
||||
|
||||
EigenvalueDecomposition helper;
|
||||
// this.m_Counter = 0;
|
||||
helper = new EigenvalueDecomposition(mC);
|
||||
mB = helper.getV(); // Return the eigenvector matrix
|
||||
eigenvalues = helper.getRealEigenvalues();
|
||||
|
||||
// double[] sqrtEig = eigenvalues.clone();
|
||||
// for (int i = 0; i < sqrtEig.length; i++) {
|
||||
// sqrtEig[i] = Math.sqrt(eigenvalues[i]);
|
||||
// }
|
||||
// mB.times(sqrtEig, mBD);
|
||||
|
||||
// Matrix test = (Matrix)mB.clone();
|
||||
// System.out.println(test);
|
||||
// System.out.println(test.transpose());
|
||||
// System.out.println(test.times(test.transpose()));
|
||||
// test = (Matrix)mB.clone();
|
||||
// double[] mult = new double[dim];
|
||||
// int spalte=3;
|
||||
// for (int i=0; i<dim; i++) {
|
||||
// System.out.println(test.get(i,spalte));
|
||||
// for (int j=0; j<dim; j++) mult[i] += mC.get(i,j)*test.get(j, spalte);
|
||||
// }
|
||||
// System.out.println("eigenv: " + eigenvalues[spalte]);
|
||||
// System.out.println(BeanInspector.toString(mult));
|
||||
// System.exit(1);
|
||||
}
|
||||
|
||||
/**
|
||||
* calculate weighted mean of the selected population
|
||||
* @param selectedPop
|
||||
* @return
|
||||
*/
|
||||
private double[] calcMeanX(Population selectedPop) {
|
||||
return selectedPop.getCenterWeighted(weights);
|
||||
}
|
||||
|
||||
private double getWeight(int i) {
|
||||
return weights[i];
|
||||
}
|
||||
|
||||
private void initWeights(int mu, int lambda) {
|
||||
weights = new double[mu];
|
||||
double sum = 0;
|
||||
int type = 0; // zero is default log scale
|
||||
for (int i=0; i<mu; i++) {
|
||||
if (type == 0) {
|
||||
weights[i] = (Math.log((lambda+1)/2.)-Math.log(i+1));
|
||||
} else weights[i] = 1.;
|
||||
sum+=weights[i];
|
||||
}
|
||||
for (int i=0; i<mu; i++) weights[i] /= sum;
|
||||
}
|
||||
|
||||
public void crossoverOnStrategyParameters(AbstractEAIndividual indy1,
|
||||
Population partners) {
|
||||
// nothing to do
|
||||
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return "Rank-Mu-CMA-Mutator";
|
||||
}
|
||||
|
||||
public String getStringRepresentation() {
|
||||
return "Rank-Mu-CMA-Mutator";
|
||||
}
|
||||
|
||||
public String globalInfo() {
|
||||
return "The CMA mutator scheme with static cov. matrix, rank-mu update and weighted recombination.";
|
||||
}
|
||||
|
||||
public void init(AbstractEAIndividual individual,
|
||||
InterfaceOptimizationProblem opt) {
|
||||
// TODO recheck all this; some is handled in adaptGeneration on the first call
|
||||
firstAdaptionDone = false;
|
||||
range = ((InterfaceDataTypeDouble)individual).getDoubleRange();
|
||||
dim = range.length;
|
||||
if (TRACE_1) System.out.println("WCMA init " + dim);
|
||||
c_c = (4./(dim+4));
|
||||
c_sig = Double.NaN; // mark as not yet initialized
|
||||
// c_u_sig = Double.NaN;
|
||||
d_sig = Double.NaN; // init in first adaption step!
|
||||
if (TRACE_1) System.out.println("WCMA static init " + dim);
|
||||
eigenvalues = new double[dim];
|
||||
Arrays.fill(eigenvalues, 1.);
|
||||
|
||||
meanX = new double[dim];
|
||||
pathC = new double[dim];
|
||||
pathS = new double[dim];
|
||||
// mBD = new double[dim];
|
||||
mC = Matrix.identity(dim, dim);
|
||||
mB = Matrix.identity(dim, dim);
|
||||
sigma = 0.2;
|
||||
z = new double[dim];
|
||||
zCor = new double[dim];
|
||||
expRandStepLen = calcExpRandStepLen();
|
||||
|
||||
}
|
||||
|
||||
public void mutate(AbstractEAIndividual individual) {
|
||||
// if (!firstAdaptionDone) {
|
||||
// if (TRACE) System.out.println("No mutation before first adaptions step");
|
||||
// return;
|
||||
// }
|
||||
if (individual instanceof InterfaceDataTypeDouble) {
|
||||
double[] x = ((InterfaceDataTypeDouble)individual).getDoubleData();
|
||||
// if (TRACE) System.out.println("WCMA mutate, bef: " + BeanInspector.toString(x));
|
||||
double[][] range = ((InterfaceDataTypeDouble)individual).getDoubleRange();
|
||||
|
||||
((InterfaceDataTypeDouble)individual).SetDoubleGenotype(mutate(x, range, 0));
|
||||
|
||||
// if (TRACE) System.out.println("WCMA mutate, aft: " + BeanInspector.toString(x));
|
||||
} else System.err.println("Error, expecting InterfaceDataTypeDouble");
|
||||
}
|
||||
|
||||
private double[] mutate(double[] x, double[][] range, int count) {
|
||||
if (firstAdaptionDone) {
|
||||
double[] artmp = new double[x.length];
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
artmp[i] = Math.sqrt(eigenvalues[i]) * RNG.gaussianDouble(1.);
|
||||
}
|
||||
// System.out.println("Sampling around " + BeanInspector.toString(meanX));
|
||||
/* add mutation (sigma * B * (D*z)) */
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
double sum = 0.;
|
||||
for (int j = 0; j < dim; ++j)
|
||||
sum += mB.get(i,j) * artmp[j];
|
||||
x[i] = meanX[i]+getSigma(i)*sum;
|
||||
}
|
||||
} else {
|
||||
// no valid meanX yet, so just do a gaussian jump with sigma
|
||||
for (int i = 0; i < dim; ++i) {
|
||||
x[i] += RNG.gaussianDouble(getSigma(i));
|
||||
}
|
||||
}
|
||||
if (isInRange(x, range)) return x;
|
||||
else {
|
||||
if (count > 5) return repairMutation(x, range); // allow some nice tries before using brute force
|
||||
else return mutate(x, range, count+1); // for really bad initial deviations this might be a quasi infinite loop
|
||||
}
|
||||
}
|
||||
|
||||
private double[] repairMutation(double[] x, double[][] range) {
|
||||
// TODO % You may handle constraints here. You may either resample
|
||||
// % arz(:,k) and/or multiply it with a factor between -1 and 1
|
||||
// % (the latter will decrease the overall step size) and
|
||||
// % recalculate arx accordingly. Do not change arx or arz in any
|
||||
// % other way.
|
||||
for (int i=0; i<x.length; i++) {
|
||||
if (x[i]<range[i][0]) x[i]=range[i][0];
|
||||
else if (x[i]>range[i][1]) x[i]=range[i][1];
|
||||
}
|
||||
return x;
|
||||
}
|
||||
|
||||
private boolean isInRange(double[] x, double[][] range) {
|
||||
for (int i=0; i<x.length; i++) {
|
||||
if (x[i]<range[i][0] || (x[i]>range[i][1])) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* After optimization start, this returns the initial sigma value
|
||||
* actually employed.
|
||||
*
|
||||
* @return the initial sigma value actually employed
|
||||
*/
|
||||
public double getFirstSigma() {
|
||||
return firstSigma;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the initialSig
|
||||
*/
|
||||
public InitialSigmaEnum getInitialSigma() {
|
||||
return initialSig;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param initialSig the initialSig to set
|
||||
*/
|
||||
public void setInitialSigma(InitialSigmaEnum initialSig) {
|
||||
this.initialSig = initialSig;
|
||||
}
|
||||
|
||||
public String initialSigmaTipText() {
|
||||
return "Method to use for setting the initial step size.";
|
||||
}
|
||||
|
||||
/**
|
||||
* From Auger&Hansen, CEC '05, stopping criterion TolX.
|
||||
*
|
||||
* @param tolX
|
||||
* @return
|
||||
*/
|
||||
public boolean testAllDistBelow(double tolX) {
|
||||
// if all(sigma*(max(abs(pc), sqrt(diag(C)))) < stopTolX)
|
||||
boolean res = true;
|
||||
int i=0;
|
||||
while (res && i<dim) {
|
||||
res = res && (getSigma(i)*Math.max(Math.abs(pathC[i]), Math.sqrt(mC.get(i,i))) < tolX);
|
||||
i++;
|
||||
}
|
||||
if (TRACE_TEST) if (res) System.out.println("testAllDistBelow hit");
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* From Auger&Hansen, CEC '05, stopping criterion noeffectaxis.
|
||||
* @param d
|
||||
* @param gen
|
||||
* @return
|
||||
*/
|
||||
public boolean testNoChangeAddingDevAxis(double d, int gen) {
|
||||
// if all(xmean == xmean + 0.1*sigma*BD(:,1+floor(mod(countiter,N))))
|
||||
// i = 1+floor(mod(countiter,N));
|
||||
// stopflag(end+1) = {'warnnoeffectaxis'};
|
||||
|
||||
int k = gen%dim;
|
||||
double[] ev_k = mB.getColumn(k);
|
||||
Mathematics.svMult(Math.sqrt(eigenvalues[k]), ev_k, ev_k); // this is now e_k*v_k = BD(:,...)
|
||||
|
||||
int i=0;
|
||||
boolean res = true;
|
||||
while (res && (i<dim)) {
|
||||
res = res && (meanX[i] == (meanX[i] + d*getSigma(i)*ev_k[i]));
|
||||
i++;
|
||||
}
|
||||
if (TRACE_TEST) if (res) System.out.println("testNoChangeAddingDevAxis hit");
|
||||
return res;
|
||||
}
|
||||
|
||||
/**
|
||||
* From Auger&Hansen, CEC '05, stopping criterion noeffectcoord.
|
||||
* @param d
|
||||
* @return
|
||||
*/
|
||||
public boolean testNoEffectCoord(double d) {
|
||||
// if any(xmean == xmean + 0.2*sigma*sqrt(diag(C)))
|
||||
// stopflag(end+1) = {'warnnoeffectcoord'};
|
||||
boolean ret = false;
|
||||
int i=0;
|
||||
while ((i<dim) && !ret) {
|
||||
ret = ret || (meanX[i]==(meanX[i] + d*getSigma(i)*Math.sqrt(mC.get(i, i))));
|
||||
i++;
|
||||
}
|
||||
if (TRACE_TEST) if (ret) System.out.println("testNoEffectCoord hit");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/**
|
||||
* Test condition of C (Auger&Hansen, CEC '05, stopping criterion conditioncov).
|
||||
* Return true, if a diagonal entry is <= 0 or >= d.
|
||||
*
|
||||
* @param d
|
||||
* @return true, if a diagonal entry is <= 0 or >= d, else false
|
||||
*/
|
||||
public boolean testCCondition(double d) {
|
||||
// if (min(diag(D)) <= 0) || (max(diag(D)) > 1e14*min(diag(D)))
|
||||
// stopflag(end+1) = {'warnconditioncov'};
|
||||
Pair<Double,Double> minMax = mC.getMinMaxDiag();
|
||||
if ((minMax.head <= 0) || (minMax.tail >= d)) {
|
||||
if (TRACE_TEST) System.out.println("testCCondition hit");
|
||||
return true;
|
||||
} else return false;
|
||||
}
|
||||
}
|
||||
|
||||
enum InitialSigmaEnum {
|
||||
halfRange, avgInitialDistance;
|
||||
}
|
@ -1,121 +1,120 @@
|
||||
package eva2.server.go.operators.mutation;
|
||||
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.individuals.InterfaceDataTypeDouble;
|
||||
import eva2.server.go.individuals.InterfaceESIndividual;
|
||||
import eva2.server.go.populations.Population;
|
||||
import eva2.server.go.problems.InterfaceOptimizationProblem;
|
||||
import wsi.ra.math.RNG;
|
||||
|
||||
/**
|
||||
* Created by IntelliJ IDEA.
|
||||
* User: streiche
|
||||
* Date: 15.05.2003
|
||||
* Time: 17:04:24
|
||||
* To change this template use Options | File Templates.
|
||||
*/
|
||||
public class MutateESStandard implements InterfaceMutation, java.io.Serializable {
|
||||
protected double m_MutationStepSize = 0.1;
|
||||
|
||||
public MutateESStandard() {
|
||||
}
|
||||
|
||||
public MutateESStandard(MutateESStandard d) {
|
||||
this.m_MutationStepSize = d.m_MutationStepSize;
|
||||
}
|
||||
|
||||
/** This method will enable you to clone a given mutation operator
|
||||
* @return The clone
|
||||
*/
|
||||
public Object clone() {
|
||||
return new MutateESStandard(this);
|
||||
}
|
||||
|
||||
/** This method allows you to evaluate wether two mutation operators
|
||||
* are actually the same.
|
||||
* @param mutator The other mutation operator
|
||||
*/
|
||||
public boolean equals(Object mutator) {
|
||||
if (mutator instanceof MutateESStandard) {
|
||||
MutateESStandard mut = (MutateESStandard)mutator;
|
||||
if (this.m_MutationStepSize != mut.m_MutationStepSize) return false;
|
||||
return true;
|
||||
} else return false;
|
||||
}
|
||||
|
||||
/** This method allows you to init the mutation operator
|
||||
* @param individual The individual that will be mutated.
|
||||
* @param opt The optimization problem.
|
||||
*/
|
||||
public void init(AbstractEAIndividual individual, InterfaceOptimizationProblem opt) {
|
||||
|
||||
}
|
||||
|
||||
/** This method will mutate a given AbstractEAIndividual. If the individual
|
||||
* doesn't implement InterfaceESIndividual nothing happens.
|
||||
* @param individual The individual that is to be mutated
|
||||
*/
|
||||
public void mutate(AbstractEAIndividual individual) {
|
||||
//System.out.println("Before Mutate: " +((GAIndividual)individual).getSolutionRepresentationFor());
|
||||
if (individual instanceof InterfaceESIndividual) {
|
||||
double[] x = ((InterfaceESIndividual)individual).getDGenotype();
|
||||
double[][] range = ((InterfaceESIndividual)individual).getDoubleRange();
|
||||
for (int i = 0; i < x.length; i++) {
|
||||
x[i] += ((range[i][1] -range[i][0])/2)*RNG.gaussianDouble(this.m_MutationStepSize);
|
||||
if (range[i][0] > x[i]) x[i] = range[i][0];
|
||||
if (range[i][1] < x[i]) x[i] = range[i][1];
|
||||
}
|
||||
((InterfaceESIndividual)individual).SetDGenotype(x);
|
||||
|
||||
}
|
||||
//System.out.println("After Mutate: " +((GAIndividual)individual).getSolutionRepresentationFor());
|
||||
}
|
||||
|
||||
/** This method allows you to perform either crossover on the strategy parameters
|
||||
* or to deal in some other way with the crossover event.
|
||||
* @param indy1 The original mother
|
||||
* @param partners The original partners
|
||||
*/
|
||||
public void crossoverOnStrategyParameters(AbstractEAIndividual indy1, Population partners) {
|
||||
// nothing to do here
|
||||
}
|
||||
|
||||
/** This method allows you to get a string representation of the mutation
|
||||
* operator
|
||||
* @return A descriptive string.
|
||||
*/
|
||||
public String getStringRepresentation() {
|
||||
return "ES standard mutation";
|
||||
}
|
||||
|
||||
/**********************************************************************************************************************
|
||||
* These are for GUI
|
||||
*/
|
||||
/** This method allows the CommonJavaObjectEditorPanel to read the
|
||||
* name to the current object.
|
||||
* @return The name.
|
||||
*/
|
||||
public String getName() {
|
||||
return "ES standard mutation ";
|
||||
}
|
||||
/** This method returns a global info string
|
||||
* @return description
|
||||
*/
|
||||
public String globalInfo() {
|
||||
return "The standard mutation alters all elements of the double attributes with a fixed mutation step size.";
|
||||
}
|
||||
|
||||
/** This method allows you to set the fixed mutation step size
|
||||
* @param step The new mutation step size
|
||||
*/
|
||||
public void setMutationStepSize(double step) {
|
||||
if (step < 0) step = 0.0000001;
|
||||
this.m_MutationStepSize = step;
|
||||
}
|
||||
public double getMutationStepSize() {
|
||||
return this.m_MutationStepSize;
|
||||
}
|
||||
public String mutationStepSizeTipText() {
|
||||
return "Set the value for the fixed mutation step size.";
|
||||
}
|
||||
}
|
||||
//package eva2.server.go.operators.mutation;
|
||||
//
|
||||
//import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
//import eva2.server.go.individuals.InterfaceDataTypeDouble;
|
||||
//import eva2.server.go.individuals.InterfaceESIndividual;
|
||||
//import eva2.server.go.populations.Population;
|
||||
//import eva2.server.go.problems.InterfaceOptimizationProblem;
|
||||
//import wsi.ra.math.RNG;
|
||||
//
|
||||
///**
|
||||
// * Created by IntelliJ IDEA.
|
||||
// * User: streiche
|
||||
// * Date: 15.05.2003
|
||||
// * Time: 17:04:24
|
||||
// * To change this template use Options | File Templates.
|
||||
// */
|
||||
//public class MutateESStandard implements InterfaceMutation, java.io.Serializable {
|
||||
// protected double m_MutationStepSize = 0.1;
|
||||
// public MutateESStandard() {
|
||||
// }
|
||||
//
|
||||
// public MutateESStandard(MutateESStandard d) {
|
||||
// this.m_MutationStepSize = d.m_MutationStepSize;
|
||||
// }
|
||||
//
|
||||
// /** This method will enable you to clone a given mutation operator
|
||||
// * @return The clone
|
||||
// */
|
||||
// public Object clone() {
|
||||
// return new MutateESStandard(this);
|
||||
// }
|
||||
//
|
||||
// /** This method allows you to evaluate wether two mutation operators
|
||||
// * are actually the same.
|
||||
// * @param mutator The other mutation operator
|
||||
// */
|
||||
// public boolean equals(Object mutator) {
|
||||
// if (mutator instanceof MutateESStandard) {
|
||||
// MutateESStandard mut = (MutateESStandard)mutator;
|
||||
// if (this.m_MutationStepSize != mut.m_MutationStepSize) return false;
|
||||
// return true;
|
||||
// } else return false;
|
||||
// }
|
||||
//
|
||||
// /** This method allows you to init the mutation operator
|
||||
// * @param individual The individual that will be mutated.
|
||||
// * @param opt The optimization problem.
|
||||
// */
|
||||
// public void init(AbstractEAIndividual individual, InterfaceOptimizationProblem opt) {
|
||||
//
|
||||
// }
|
||||
//
|
||||
// /** This method will mutate a given AbstractEAIndividual. If the individual
|
||||
// * doesn't implement InterfaceESIndividual nothing happens.
|
||||
// * @param individual The individual that is to be mutated
|
||||
// */
|
||||
// public void mutate(AbstractEAIndividual individual) {
|
||||
// //System.out.println("Before Mutate: " +((GAIndividual)individual).getSolutionRepresentationFor());
|
||||
// if (individual instanceof InterfaceESIndividual) {
|
||||
// double[] x = ((InterfaceESIndividual)individual).getDGenotype();
|
||||
// double[][] range = ((InterfaceESIndividual)individual).getDoubleRange();
|
||||
// for (int i = 0; i < x.length; i++) {
|
||||
// x[i] += ((range[i][1] -range[i][0])/2)*RNG.gaussianDouble(this.m_MutationStepSize);
|
||||
// if (range[i][0] > x[i]) x[i] = range[i][0];
|
||||
// if (range[i][1] < x[i]) x[i] = range[i][1];
|
||||
// }
|
||||
// ((InterfaceESIndividual)individual).SetDGenotype(x);
|
||||
//
|
||||
// }
|
||||
// //System.out.println("After Mutate: " +((GAIndividual)individual).getSolutionRepresentationFor());
|
||||
// }
|
||||
//
|
||||
// /** This method allows you to perform either crossover on the strategy parameters
|
||||
// * or to deal in some other way with the crossover event.
|
||||
// * @param indy1 The original mother
|
||||
// * @param partners The original partners
|
||||
// */
|
||||
// public void crossoverOnStrategyParameters(AbstractEAIndividual indy1, Population partners) {
|
||||
// // nothing to do here
|
||||
// }
|
||||
//
|
||||
// /** This method allows you to get a string representation of the mutation
|
||||
// * operator
|
||||
// * @return A descriptive string.
|
||||
// */
|
||||
// public String getStringRepresentation() {
|
||||
// return "ES standard mutation";
|
||||
// }
|
||||
//
|
||||
///**********************************************************************************************************************
|
||||
// * These are for GUI
|
||||
// */
|
||||
// /** This method allows the CommonJavaObjectEditorPanel to read the
|
||||
// * name to the current object.
|
||||
// * @return The name.
|
||||
// */
|
||||
// public String getName() {
|
||||
// return "ES standard mutation ";
|
||||
// }
|
||||
// /** This method returns a global info string
|
||||
// * @return description
|
||||
// */
|
||||
// public String globalInfo() {
|
||||
// return "The standard mutation alters all elements of the double attributes with a fixed mutation step size.";
|
||||
// }
|
||||
//
|
||||
// /** This method allows you to set the fixed mutation step size
|
||||
// * @param step The new mutation step size
|
||||
// */
|
||||
// public void setMutationStepSize(double step) {
|
||||
// if (step < 0) step = 0.0000001;
|
||||
// this.m_MutationStepSize = step;
|
||||
// }
|
||||
// public double getMutationStepSize() {
|
||||
// return this.m_MutationStepSize;
|
||||
// }
|
||||
// public String mutationStepSizeTipText() {
|
||||
// return "Set the value for the fixed mutation step size.";
|
||||
// }
|
||||
//}
|
||||
|
@ -14,11 +14,7 @@ import wsi.ra.math.RNG;
|
||||
* Time: 14:11:49
|
||||
* To change this template use File | Settings | File Templates.
|
||||
*/
|
||||
public class MutateESSuccessRule extends MutateESStandard implements InterfaceMutation, java.io.Serializable {
|
||||
/*
|
||||
* This is a bit of a cheat as the implementation does only hold some
|
||||
* more parameters while the ES strategy really acts on it.
|
||||
*/
|
||||
public class MutateESSuccessRule extends MutateESFixedStepSize implements InterfaceMutationGenerational, java.io.Serializable {
|
||||
// it would be quite nice to make this variable static, but in that case
|
||||
// no one could runs n independent ES runs in parallel anymore *sigh*
|
||||
// protected static double m_MutationStepSize = 0.2;
|
||||
@ -30,7 +26,7 @@ public class MutateESSuccessRule extends MutateESStandard implements InterfaceMu
|
||||
}
|
||||
|
||||
public MutateESSuccessRule(MutateESSuccessRule mutator) {
|
||||
this.m_MutationStepSize = mutator.m_MutationStepSize;
|
||||
super(mutator);
|
||||
this.m_SuccessRate = mutator.m_SuccessRate;
|
||||
this.m_Alpha = mutator.m_Alpha;
|
||||
}
|
||||
@ -49,12 +45,13 @@ public class MutateESSuccessRule extends MutateESStandard implements InterfaceMu
|
||||
public boolean equals(Object mutator) {
|
||||
if (mutator instanceof MutateESSuccessRule) {
|
||||
MutateESSuccessRule mut = (MutateESSuccessRule)mutator;
|
||||
if (this.m_MutationStepSize != mut.m_MutationStepSize) return false;
|
||||
if (this.m_Sigma != mut.m_Sigma) return false;
|
||||
if (this.m_SuccessRate != mut.m_SuccessRate) return false;
|
||||
if (this.m_Alpha != mut.m_Alpha) return false;
|
||||
return true;
|
||||
} else return false;
|
||||
}
|
||||
|
||||
/** This method allows you to get a string representation of the mutation
|
||||
* operator
|
||||
* @return A descriptive string.
|
||||
@ -66,12 +63,12 @@ public class MutateESSuccessRule extends MutateESStandard implements InterfaceMu
|
||||
/** This method increases the mutation step size.
|
||||
*/
|
||||
public void increaseMutationStepSize() {
|
||||
this.m_MutationStepSize = this.m_MutationStepSize * this.m_Alpha;
|
||||
this.m_Sigma = this.m_Sigma * this.m_Alpha;
|
||||
}
|
||||
/** This method decrease the mutation step size.
|
||||
*/
|
||||
public void decreaseMutationStepSize() {
|
||||
this.m_MutationStepSize = this.m_MutationStepSize / this.m_Alpha;
|
||||
this.m_Sigma = this.m_Sigma / this.m_Alpha;
|
||||
}
|
||||
|
||||
/**********************************************************************************************************************
|
||||
@ -121,6 +118,36 @@ public class MutateESSuccessRule extends MutateESStandard implements InterfaceMu
|
||||
return this.m_Alpha;
|
||||
}
|
||||
public String alphaTipText() {
|
||||
return "Choose the factor by which the mutation step size is to be increased/decreased.";
|
||||
return "Choose the factor > 1 by which the mutation step size is to be increased/decreased.";
|
||||
}
|
||||
|
||||
public void adaptAfterSelection(Population oldGen, Population selected) {
|
||||
// nothing to do here
|
||||
}
|
||||
|
||||
public void adaptGenerational(Population selectedPop, Population parentPop, Population newPop, boolean updateSelected) {
|
||||
double rate = 0.;
|
||||
for (int i = 0; i < parentPop.size(); i++) {
|
||||
// calculate success rate
|
||||
// System.out.println("new fit / old fit: " + BeanInspector.toString(newPop.getEAIndividual(i).getFitness()) + " , " + BeanInspector.toString(parentPop.getEAIndividual(i).getFitness()));
|
||||
if (newPop.getEAIndividual(i).getFitness(0) < parentPop.getEAIndividual(i).getFitness(0)) rate++;
|
||||
}
|
||||
rate = rate / parentPop.size();
|
||||
|
||||
if (updateSelected) for (int i = 0; i < selectedPop.size(); i++) { // applied to the old population as well in case of plus strategy
|
||||
MutateESSuccessRule mutator = (MutateESSuccessRule)((AbstractEAIndividual)selectedPop.get(i)).getMutationOperator();
|
||||
updateMutator(rate, mutator);
|
||||
// System.out.println("old pop step size " + mutator.getSigma()+ " (" + mutator+ ")");
|
||||
}
|
||||
for (int i = 0; i < newPop.size(); i++) {
|
||||
MutateESSuccessRule mutator = (MutateESSuccessRule)((AbstractEAIndividual)newPop.get(i)).getMutationOperator();
|
||||
updateMutator(rate, mutator);
|
||||
// System.out.println("new pop step size " + mutator.getSigma()+ " (" + mutator+ ")");
|
||||
}
|
||||
}
|
||||
|
||||
private void updateMutator(double rate, MutateESSuccessRule mutator) {
|
||||
if (rate < mutator.getSuccessRate()) mutator.decreaseMutationStepSize();
|
||||
else mutator.increaseMutationStepSize();
|
||||
}
|
||||
}
|
@ -62,6 +62,14 @@ Serializable {
|
||||
else convergenceCondition.setSelectedTag("Relative");
|
||||
}
|
||||
|
||||
public FitnessConvergenceTerminator(FitnessConvergenceTerminator other) {
|
||||
pMetric = new PhenotypeMetric();
|
||||
convThresh = other.convThresh;
|
||||
this.m_stagTime = other.m_stagTime;
|
||||
stagnationMeasure.setSelectedTag(other.getStagnationMeasure().getSelectedTagID());
|
||||
convergenceCondition.setSelectedTag(other.getConvergenceCondition().getSelectedTagID());
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
*/
|
||||
|
@ -941,6 +941,9 @@ public class Population extends ArrayList implements PopulationInterface, Clonea
|
||||
|
||||
/**
|
||||
* Fire an event every n function calls, the event sends the public String funCallIntervalReached.
|
||||
* Be aware that if this interval is smaller than the population size, it may happen that a notification
|
||||
* is fired before all individuals have been evaluated once, meaning that a false zero fitness
|
||||
* appears at the beginning of the optimization.
|
||||
*
|
||||
* @param notifyEvalInterval the notifyEvalInterval to set
|
||||
*/
|
||||
|
@ -56,7 +56,7 @@ public abstract class AbstractOptimizationProblem implements InterfaceOptimizati
|
||||
// System.err.println("Population evaluation seems not required!");
|
||||
// } else {
|
||||
// @todo This is the position to implement a granular
|
||||
// @todo paralliziation scheme
|
||||
// @todo paralleliziation scheme
|
||||
evaluatePopulationStart(population);
|
||||
for (int i = 0; i < population.size(); i++) {
|
||||
tmpIndy = (AbstractEAIndividual) population.get(i);
|
||||
|
@ -90,8 +90,10 @@ public class CHCAdaptiveSearchAlgorithm implements InterfaceOptimizer, java.io.S
|
||||
System.out.println("Problem does not apply InterfaceGAIndividual, which is the only individual type valid for CHC!");
|
||||
}
|
||||
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
|
@ -124,9 +124,11 @@ public class ClusteringHillClimbing implements InterfacePopulationChangedEventLi
|
||||
loopCnt = 0;
|
||||
this.m_Population = (Population)pop.clone();
|
||||
m_Population.addPopulationChangedEventListener(null);
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** Something has changed
|
||||
|
@ -93,11 +93,13 @@ public class DifferentialEvolution implements InterfaceOptimizer, java.io.Serial
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
// if (reset) this.m_Population.init();
|
||||
// else children = new Population(m_Population.size());
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
|
@ -1,7 +1,10 @@
|
||||
package eva2.server.go.strategies;
|
||||
|
||||
import eva2.gui.BeanInspector;
|
||||
import eva2.gui.GenericObjectEditor;
|
||||
import eva2.server.go.InterfacePopulationChangedEventListener;
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.operators.mutation.InterfaceMutationGenerational;
|
||||
import eva2.server.go.operators.mutation.MutateESSuccessRule;
|
||||
import eva2.server.go.operators.selection.InterfaceSelection;
|
||||
import eva2.server.go.operators.selection.SelectBestIndividuals;
|
||||
@ -33,7 +36,6 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
//private double m_MyuRatio = 6;
|
||||
private int m_Mu = 5;
|
||||
private int m_Lambda = 20;
|
||||
private int m_InitialPopulationSize = 0;
|
||||
private boolean m_UsePlusStrategy = false;
|
||||
private Population m_Population = new Population();
|
||||
private InterfaceOptimizationProblem m_Problem = new B1Problem();
|
||||
@ -42,7 +44,7 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
private InterfaceSelection m_EnvironmentSelection = new SelectBestIndividuals();
|
||||
private int m_NumberOfPartners = 1;
|
||||
private int origPopSize = -1; // especially for CBN
|
||||
private double[] m_FitnessOfParents = null;
|
||||
// private double[] m_FitnessOfParents = null;
|
||||
private boolean forceOrigPopSize = true;// especially for CBN
|
||||
|
||||
transient private String m_Identifier = "";
|
||||
@ -64,7 +66,6 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
this.m_Problem = (InterfaceOptimizationProblem)a.m_Problem.clone();
|
||||
this.m_Mu = a.m_Mu;
|
||||
this.m_Lambda = a.m_Lambda;
|
||||
this.m_InitialPopulationSize = a.m_InitialPopulationSize;
|
||||
this.m_UsePlusStrategy = a.m_UsePlusStrategy;
|
||||
this.m_NumberOfPartners = a.m_NumberOfPartners;
|
||||
this.m_ParentSelection = (InterfaceSelection)a.m_ParentSelection.clone();
|
||||
@ -72,6 +73,10 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
this.m_EnvironmentSelection = (InterfaceSelection)a.m_EnvironmentSelection.clone();
|
||||
}
|
||||
|
||||
public void hideHideable() {
|
||||
GenericObjectEditor.setHideProperty(this.getClass(), "population", true);
|
||||
}
|
||||
|
||||
public Object clone() {
|
||||
return (Object) new EvolutionStrategies(this);
|
||||
}
|
||||
@ -86,7 +91,7 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
this.m_Problem.initPopulation(this.m_Population);
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
// this.m_Population.setPopulationSize(orgPopSize);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
// this.firePropertyChangedEvent("NextGenerationPerformed");// not necessary if incrGeneration is called
|
||||
}
|
||||
|
||||
|
||||
@ -98,9 +103,11 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
origPopSize = pop.getPopulationSize();
|
||||
// System.out.println("ES: orig popsize is " + origPopSize);
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
// this.firePropertyChangedEvent("NextGenerationPerformed"); // not necessary if incrGeneration is called
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
@ -129,94 +136,88 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
/** This method will generate the offspring population from the
|
||||
* given population of evaluated individuals.
|
||||
*/
|
||||
private Population generateChildren() {
|
||||
Population result = this.m_Population.cloneWithoutInds(), parents;
|
||||
protected Population generateEvalChildren(Population fromPopulation) {
|
||||
Population result = m_Population.cloneWithoutInds(), parents;
|
||||
AbstractEAIndividual[] offSprings;
|
||||
AbstractEAIndividual tmpIndy;
|
||||
|
||||
result.clear();
|
||||
this.m_ParentSelection.prepareSelection(this.m_Population);
|
||||
this.m_PartnerSelection.prepareSelection(this.m_Population);
|
||||
parents = this.m_ParentSelection.selectFrom(this.m_Population, this.m_Lambda);
|
||||
this.m_ParentSelection.prepareSelection(fromPopulation);
|
||||
this.m_PartnerSelection.prepareSelection(fromPopulation);
|
||||
parents = this.m_ParentSelection.selectFrom(fromPopulation, this.m_Lambda);
|
||||
|
||||
for (int i = 0; i < parents.size(); i++) {
|
||||
tmpIndy = (AbstractEAIndividual)parents.get(i);
|
||||
if (tmpIndy == null) System.out.println("Individual null "+i);
|
||||
if (parents == null) System.out.println("parents null "+i);
|
||||
if (tmpIndy.getMutationOperator() instanceof MutateESSuccessRule) {
|
||||
if (this.m_FitnessOfParents == null) this.m_FitnessOfParents = new double[this.m_Lambda];
|
||||
this.m_FitnessOfParents[i] = tmpIndy.getFitness(0);
|
||||
}
|
||||
offSprings = tmpIndy.mateWith(this.m_PartnerSelection.findPartnerFor(tmpIndy, this.m_Population, this.m_NumberOfPartners));
|
||||
// for (int j = 0; j < offSprings.length; j++) {
|
||||
// offSprings[j].mutate();
|
||||
// }
|
||||
offSprings = tmpIndy.mateWith(this.m_PartnerSelection.findPartnerFor(tmpIndy, fromPopulation, this.m_NumberOfPartners));
|
||||
offSprings[0].mutate();
|
||||
result.add(i, offSprings[0]);
|
||||
}
|
||||
this.evaluatePopulation(result);
|
||||
|
||||
if (result.getEAIndividual(0).getMutationOperator() instanceof InterfaceMutationGenerational) {
|
||||
// this seems to be the right moment for the 1/5-success rule
|
||||
// parents and result have the same size and correspond per individual
|
||||
((InterfaceMutationGenerational)parents.getEAIndividual(0).getMutationOperator()).adaptGenerational(fromPopulation, parents, result, m_UsePlusStrategy);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
protected Population selectParents() {
|
||||
this.m_EnvironmentSelection.prepareSelection(this.m_Population);
|
||||
return this.m_EnvironmentSelection.selectFrom(this.m_Population, this.m_Mu);
|
||||
}
|
||||
|
||||
/** The optimize method will compute a 'improved' and evaluated population
|
||||
*/
|
||||
public void optimize() {
|
||||
Population nextGeneration, parents;
|
||||
|
||||
// // calculate myu and lambda from the current population size and settings
|
||||
// if (this.m_UsePlusStrategy) {
|
||||
// this.m_Myu = (int)Math.round((this.m_Population.size()/this.m_MyuRatio) - (this.m_Population.size()/Math.pow(this.m_MyuRatio, 2)));
|
||||
// this.m_Myu = Math.max(1, this.m_Myu);
|
||||
// this.m_Lambda = this.m_Population.size() - this.m_Myu;
|
||||
//// System.out.println("Parameters: (Pop.size:"+this.m_Population.size()+"; MyuRatio:"+this.m_MyuRatio+")");
|
||||
//// System.out.println("Population Strategy: ("+ this.m_Myu+"+"+this.m_Lambda+")");
|
||||
// }
|
||||
// else {
|
||||
// this.m_Lambda = this.m_Population.size();
|
||||
// this.m_Myu = (int)Math.round(this.m_Population.size()/this.m_MyuRatio);
|
||||
// this.m_Myu = Math.max(1, this.m_Myu);
|
||||
//// System.out.println("Parameters: (Pop.size:"+this.m_Population.size()+"; MyuRatio:"+this.m_MyuRatio+")");
|
||||
//// System.out.println("Population Strategy: ("+ this.m_Myu+","+this.m_Lambda+")");
|
||||
// }
|
||||
//System.out.println("optimize");
|
||||
|
||||
// first perform the environment selection to select myu parents
|
||||
this.m_EnvironmentSelection.prepareSelection(this.m_Population);
|
||||
parents = this.m_EnvironmentSelection.selectFrom(this.m_Population, this.m_Mu);
|
||||
this.m_Population.clear();
|
||||
this.m_Population.addPopulation(parents);
|
||||
parents = selectParents();
|
||||
|
||||
// System.out.println("-- selected avg fit " + BeanInspector.toString(parents.getMeanFitness()) + " from last gen " + BeanInspector.toString(m_Population.getMeanFitness()));
|
||||
|
||||
// m_Population / parents are of sizes lambda / mu
|
||||
if (parents.getEAIndividual(0).getMutationOperator() instanceof InterfaceMutationGenerational) {
|
||||
((InterfaceMutationGenerational)parents.getEAIndividual(0).getMutationOperator()).adaptAfterSelection(getPopulation(), parents);
|
||||
}
|
||||
|
||||
// now generate the lambda offsprings
|
||||
this.m_FitnessOfParents = null;
|
||||
nextGeneration = this.generateChildren();
|
||||
this.evaluatePopulation(nextGeneration);
|
||||
if ((this.m_FitnessOfParents != null) && (((AbstractEAIndividual)parents.get(0)).getMutationOperator() instanceof MutateESSuccessRule)) {
|
||||
double rate = 0;
|
||||
|
||||
for (int i = 0; i < this.m_FitnessOfParents.length; i++) {
|
||||
if (((AbstractEAIndividual)nextGeneration.get(i)).getFitness(0) < this.m_FitnessOfParents[i]) rate++;
|
||||
}
|
||||
this.applySuccessRule((rate/((double)this.m_FitnessOfParents.length)), this.m_Population, nextGeneration);
|
||||
}
|
||||
if (this.m_UsePlusStrategy) nextGeneration.addPopulation(this.m_Population);
|
||||
nextGeneration = this.generateEvalChildren(parents); // create lambda new ones from mu parents
|
||||
|
||||
if (forceOrigPopSize && (origPopSize > 0) && (origPopSize < nextGeneration.size())) {
|
||||
// this is especially for CBN:
|
||||
this.m_EnvironmentSelection.prepareSelection(nextGeneration);
|
||||
Population tmpPop = (Population)nextGeneration.clone();
|
||||
nextGeneration.clear();
|
||||
nextGeneration.addPopulation(this.m_EnvironmentSelection.selectFrom(tmpPop, origPopSize));
|
||||
// System.out.println("ES post selection! " + origPopSize + " from " + tmpPop.size());
|
||||
m_Population = nextGeneration;
|
||||
} else {
|
||||
if ((origPopSize > 0) && (origPopSize != nextGeneration.size())) {
|
||||
System.err.println("Warning in ES! orig: " + origPopSize + " / " + nextGeneration.size());
|
||||
}
|
||||
this.m_Population = nextGeneration;
|
||||
}
|
||||
//System.out.println("Population size: " + this.m_Population.size());
|
||||
//System.out.println("-- Best Fitness " + this.m_Population.getBestFitness()[0]);
|
||||
if (this.isPlusStrategy()) nextGeneration.addPopulation(parents);
|
||||
|
||||
setPop(getReplacePop(nextGeneration));
|
||||
// System.out.println("Population size: " + this.m_Population.size());
|
||||
// System.out.println("-- Best Fitness " + this.m_Population.getBestFitness()[0]);
|
||||
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed"); // necessary here because evalPop was not called on m_Population
|
||||
}
|
||||
|
||||
/**
|
||||
* Usually, this just returns the given population.
|
||||
* However, in case of CBN this method prepares the next generation according to the species size.
|
||||
*
|
||||
* @param nextGeneration
|
||||
* @return
|
||||
*/
|
||||
protected Population getReplacePop(Population nextGeneration) {
|
||||
if (forceOrigPopSize && (origPopSize > 0) && (origPopSize < nextGeneration.size())) {
|
||||
// this is especially for CBN:
|
||||
this.m_EnvironmentSelection.prepareSelection(nextGeneration);
|
||||
Population tmpPop = (Population)nextGeneration.clone();
|
||||
nextGeneration.clear();
|
||||
nextGeneration.addPopulation(this.m_EnvironmentSelection.selectFrom(tmpPop, origPopSize));
|
||||
// System.out.println("ES post selection! " + origPopSize + " from " + tmpPop.size());
|
||||
} else {
|
||||
if ((origPopSize > 0) && (origPopSize != nextGeneration.size())) {
|
||||
System.err.println("Warning in ES! orig: " + origPopSize + " / " + nextGeneration.size());
|
||||
}
|
||||
}
|
||||
return nextGeneration;
|
||||
}
|
||||
|
||||
/** This method is just a shortcut to set the mutation step size for
|
||||
@ -227,46 +228,48 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
* @param oldPop The old population
|
||||
* @param newPop The new population
|
||||
*/
|
||||
private void applySuccessRule(double successRate, Population oldPop, Population newPop) {
|
||||
MutateESSuccessRule mutator = (MutateESSuccessRule)((AbstractEAIndividual)oldPop.get(0)).getMutationOperator();
|
||||
boolean success = (successRate < mutator.getSuccessRate());
|
||||
// this was the old solution when the mutation step size was still static
|
||||
// if (successRate < mutator.getSuccessRate()) {
|
||||
// mutator.decreaseMutationStepSize();
|
||||
// } else {
|
||||
// mutator.increaseMutationStepSize();
|
||||
// private void applySuccessRule(double successRate, Population oldPop, Population newPop) {
|
||||
// MutateESSuccessRule mutator = (MutateESSuccessRule)((AbstractEAIndividual)oldPop.get(0)).getMutationOperator();
|
||||
// boolean success = (successRate < mutator.getSuccessRate());
|
||||
// // this was the old solution when the mutation step size was still static
|
||||
//// if (successRate < mutator.getSuccessRate()) {
|
||||
//// mutator.decreaseMutationStepSize();
|
||||
//// } else {
|
||||
//// mutator.increaseMutationStepSize();
|
||||
//// }
|
||||
// if (isPlusStrategy()) for (int i = 0; i < oldPop.size(); i++) { // applied to the old population as well for plus strategy
|
||||
// if (((AbstractEAIndividual)oldPop.get(i)).getMutationOperator() instanceof MutateESSuccessRule) {
|
||||
// mutator = (MutateESSuccessRule)((AbstractEAIndividual)oldPop.get(i)).getMutationOperator();
|
||||
// if (success) mutator.decreaseMutationStepSize();
|
||||
// else mutator.increaseMutationStepSize();
|
||||
// System.out.println("old pop step size " + mutator.getSigma()+ " (" + mutator+ ")");
|
||||
// }
|
||||
// }
|
||||
for (int i = 0; i < oldPop.size(); i++) {
|
||||
if (((AbstractEAIndividual)oldPop.get(i)).getMutationOperator() instanceof MutateESSuccessRule) {
|
||||
mutator = (MutateESSuccessRule)((AbstractEAIndividual)oldPop.get(i)).getMutationOperator();
|
||||
if (success) mutator.decreaseMutationStepSize();
|
||||
else mutator.increaseMutationStepSize();
|
||||
}
|
||||
}
|
||||
for (int i = 0; i < newPop.size(); i++) {
|
||||
if (((AbstractEAIndividual)newPop.get(i)).getMutationOperator() instanceof MutateESSuccessRule) {
|
||||
mutator = (MutateESSuccessRule)((AbstractEAIndividual)newPop.get(i)).getMutationOperator();
|
||||
if (success) mutator.decreaseMutationStepSize();
|
||||
else mutator.increaseMutationStepSize();
|
||||
}
|
||||
}
|
||||
this.m_FitnessOfParents = null;
|
||||
}
|
||||
// for (int i = 0; i < newPop.size(); i++) {
|
||||
// if (((AbstractEAIndividual)newPop.get(i)).getMutationOperator() instanceof MutateESSuccessRule) {
|
||||
// mutator = (MutateESSuccessRule)((AbstractEAIndividual)newPop.get(i)).getMutationOperator();
|
||||
// if (success) mutator.decreaseMutationStepSize();
|
||||
// else mutator.increaseMutationStepSize();
|
||||
// System.out.println("new pop step size " + mutator.getSigma() + " (" + mutator+ ")");
|
||||
// }
|
||||
// }
|
||||
//// this.m_FitnessOfParents = null;
|
||||
// }
|
||||
|
||||
/** This is for debugging only
|
||||
*/
|
||||
private String showFitness(Population pop) {
|
||||
String result = "";
|
||||
AbstractEAIndividual indy;
|
||||
double[] fitness;
|
||||
for (int i = 0; i < pop.size(); i++) {
|
||||
indy = (AbstractEAIndividual)pop.get(i);
|
||||
fitness = indy.getFitness();
|
||||
for (int j = 0; j < fitness.length; j++) result += fitness[j] +"; ";
|
||||
result += "\n";
|
||||
}
|
||||
return result;
|
||||
}
|
||||
// /** This is for debugging only
|
||||
// */
|
||||
// private String showFitness(Population pop) {
|
||||
// String result = "";
|
||||
// AbstractEAIndividual indy;
|
||||
// double[] fitness;
|
||||
// for (int i = 0; i < pop.size(); i++) {
|
||||
// indy = (AbstractEAIndividual)pop.get(i);
|
||||
// fitness = indy.getFitness();
|
||||
// for (int j = 0; j < fitness.length; j++) result += fitness[j] +"; ";
|
||||
// result += "\n";
|
||||
// }
|
||||
// return result;
|
||||
// }
|
||||
|
||||
/** This method allows you to add the LectureGUI as listener to the Optimizer
|
||||
* @param ea
|
||||
@ -276,7 +279,7 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
}
|
||||
/** Something has changed
|
||||
*/
|
||||
protected void firePropertyChangedEvent (String name) {
|
||||
protected void firePropertyChangedEvent(String name) {
|
||||
if (this.m_Listener != null) this.m_Listener.registerPopulationStateChanged(this, name);
|
||||
}
|
||||
|
||||
@ -354,7 +357,7 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
* @return The name of the algorithm
|
||||
*/
|
||||
public String getName() {
|
||||
return "("+getMu()+(getPlusStrategy() ? "+" : ",")+getLambda()+")-ES";
|
||||
return "("+getMu()+(isPlusStrategy() ? "+" : ",")+getLambda()+")-ES";
|
||||
}
|
||||
|
||||
/**
|
||||
@ -366,6 +369,12 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
public Population getPopulation() {
|
||||
return this.m_Population;
|
||||
}
|
||||
|
||||
// for internal usage
|
||||
protected void setPop(Population pop) {
|
||||
m_Population = pop;
|
||||
}
|
||||
|
||||
public void setPopulation(Population pop){
|
||||
origPopSize = pop.size();
|
||||
// System.out.println("ES: orig popsize is " + origPopSize);
|
||||
@ -437,7 +446,7 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
this.m_UsePlusStrategy = elitism;
|
||||
this.checkPopulationConstraints();
|
||||
}
|
||||
public boolean getPlusStrategy() {
|
||||
public boolean isPlusStrategy() {
|
||||
return this.m_UsePlusStrategy;
|
||||
}
|
||||
public String plusStrategyTipText() {
|
||||
@ -513,17 +522,4 @@ public class EvolutionStrategies implements InterfaceOptimizer, java.io.Serializ
|
||||
public String lambdaTipText() {
|
||||
return "This is the children population size.";
|
||||
}
|
||||
|
||||
/** Set an initial population size (if smaller lambda this is ignored).
|
||||
* @param l The inital population size.
|
||||
*/
|
||||
public void setInitialPopulationSize(int l) {
|
||||
this.m_InitialPopulationSize = l;
|
||||
}
|
||||
public int getInitialPopulationSize() {
|
||||
return this.m_InitialPopulationSize;
|
||||
}
|
||||
public String initialPopulationSizeTipText() {
|
||||
return "Set an initial population size (if smaller lambda this is ignored).";
|
||||
}
|
||||
}
|
||||
|
251
src/eva2/server/go/strategies/EvolutionStrategyIPOP.java
Normal file
251
src/eva2/server/go/strategies/EvolutionStrategyIPOP.java
Normal file
@ -0,0 +1,251 @@
|
||||
package eva2.server.go.strategies;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.LinkedList;
|
||||
|
||||
import eva2.gui.GenericObjectEditor;
|
||||
import eva2.server.go.InterfacePopulationChangedEventListener;
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.operators.mutation.MutateESRankMuCMA;
|
||||
import eva2.server.go.operators.terminators.FitnessConvergenceTerminator;
|
||||
import eva2.server.go.populations.Population;
|
||||
import eva2.server.go.populations.SolutionSet;
|
||||
|
||||
/**
|
||||
* This implements the IPOP (increased population size restart) strategy ES, which increases
|
||||
* the ES population size (lambda) after phases or stagnation and restarts the optimization.
|
||||
* Stagnation is for this implementation defined by a FitnessConvergenceTerminator instance
|
||||
* which terminates if the absolute change in fitness is below a threshold (default 10e-12) for a
|
||||
* certain number of generations (default: 10+floor(30*n/lambda) for problem dimension n).
|
||||
*
|
||||
* If the MutateESRankMuCMA mutation operator is used, additional criteria are used for restarts,
|
||||
* such as numeric conditions of the covariance matrix.
|
||||
* Lambda is increased multiplicatively for every restart, and typical initial values are
|
||||
* mu=5, lambda=10, incFact=2.
|
||||
* The IPOP-CMA-ES won the CEC 2005 benchmark challenge.
|
||||
* Refer to Auger&Hansen 05 for more details.
|
||||
*
|
||||
* A.Auger & N.Hansen. A Restart CMA Evolution Strategy With Increasing Population Size. CEC 2005.
|
||||
*
|
||||
* @author mkron
|
||||
*
|
||||
*/
|
||||
public class EvolutionStrategyIPOP extends EvolutionStrategies implements InterfacePopulationChangedEventListener {
|
||||
private static final long serialVersionUID = 4102736881931867818L;
|
||||
int dim = -1;
|
||||
int initialLambda = 10;
|
||||
|
||||
private double stagThreshold = 10e-12;
|
||||
private int stagTime = -1;
|
||||
|
||||
double incPopSizeFact = 2.;
|
||||
FitnessConvergenceTerminator fitConvTerm = null;
|
||||
LinkedList<AbstractEAIndividual> bestList = null;
|
||||
AbstractEAIndividual best = null;
|
||||
|
||||
public EvolutionStrategyIPOP() {
|
||||
super();
|
||||
setMu(5);
|
||||
setLambda(10);
|
||||
}
|
||||
|
||||
public EvolutionStrategyIPOP(EvolutionStrategyIPOP other) {
|
||||
dim = other.dim;
|
||||
initialLambda = other.initialLambda;
|
||||
incPopSizeFact = other.incPopSizeFact;
|
||||
stagThreshold = other.stagThreshold;
|
||||
stagTime = other.stagTime;
|
||||
|
||||
if (other.fitConvTerm != null) fitConvTerm = new FitnessConvergenceTerminator(other.fitConvTerm);
|
||||
}
|
||||
|
||||
public Object clone() {
|
||||
return new EvolutionStrategyIPOP(this);
|
||||
}
|
||||
|
||||
/** The optimize method will compute a 'improved' and evaluated population
|
||||
*/
|
||||
public void optimize() {
|
||||
// Population nextGeneration, parents;
|
||||
//
|
||||
// // first perform the environment selection to select myu parents
|
||||
// parents = selectParents();
|
||||
//
|
||||
// // m_Population / parents are of sizes lambda / mu
|
||||
// if (parents.getEAIndividual(0).getMutationOperator() instanceof InterfaceMutationGenerational) {
|
||||
// ((InterfaceMutationGenerational)parents.getEAIndividual(0).getMutationOperator()).adaptAfterSelection(getPopulation(), parents);
|
||||
// }
|
||||
//
|
||||
// // now generate the lambda offsprings
|
||||
// nextGeneration = this.generateEvalChildren(parents); // create lambda new ones from mu parents
|
||||
//
|
||||
// if (this.isPlusStrategy()) nextGeneration.addPopulation(parents);
|
||||
//
|
||||
// setPop(getReplacePop(nextGeneration));
|
||||
//
|
||||
// this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
//////////////////////////
|
||||
super.optimize();
|
||||
|
||||
// remember the best indy
|
||||
if ((best == null) || !best.isDominating(getPopulation().getBestEAIndividual())) {
|
||||
best = getPopulation().getBestEAIndividual();
|
||||
}
|
||||
if (testIPOPStopCrit(getPopulation())) {
|
||||
// reinitialize population with increased mu,lambda
|
||||
boostPopSize();
|
||||
}
|
||||
}
|
||||
|
||||
public void hideHideable() {
|
||||
GenericObjectEditor.setHideProperty(this.getClass(), "population", true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reinitialize population with increased mu,lambda
|
||||
**/
|
||||
private void boostPopSize() {
|
||||
// increase by at least one
|
||||
int newLambda = Math.max((int)(getLambda()*incPopSizeFact), getLambda() + 1);
|
||||
super.setLambda(newLambda);
|
||||
bestList.add(best);
|
||||
best = null;
|
||||
Population newPop = getPopulation().cloneWithoutInds();
|
||||
getProblem().initPopulation(newPop);
|
||||
double[] badFit = getPopulation().getBestFitness().clone();
|
||||
Arrays.fill(badFit, Double.MAX_VALUE);
|
||||
newPop.setAllFitnessValues(badFit);
|
||||
getPopulation().clear();
|
||||
getPopulation().addAll(newPop);
|
||||
getProblem().evaluate(getPopulation());
|
||||
}
|
||||
|
||||
protected void firePropertyChangedEvent(String name) {
|
||||
if (name.equals(Population.funCallIntervalReached)) {
|
||||
super.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
else {} // nothing, evt is produced in #registerPopulationStateChanged, dont forward original due to changing pop size
|
||||
}
|
||||
|
||||
public void init() {
|
||||
// setMu(initialMu);
|
||||
super.setLambda(initialLambda);
|
||||
getPopulation().setNotifyEvalInterval(initialLambda);
|
||||
super.init();
|
||||
bestList = new LinkedList<AbstractEAIndividual>();
|
||||
best = getPopulation().getBestEAIndividual();
|
||||
dim = AbstractEAIndividual.getDoublePosition(getPopulation().getEAIndividual(0)).length;
|
||||
|
||||
stagTime = (int)(10+Math.floor(30*dim/getPopulation().size()));
|
||||
|
||||
fitConvTerm = new FitnessConvergenceTerminator(stagThreshold, stagTime, false, true); // gen. based, absolute
|
||||
getPopulation().addPopulationChangedEventListener(this);
|
||||
getPopulation().setNotifyEvalInterval(initialLambda);
|
||||
}
|
||||
|
||||
/**
|
||||
* Test for the IPOP stopping criteria.
|
||||
* @param population
|
||||
* @return
|
||||
*/
|
||||
private boolean testIPOPStopCrit(Population pop) {
|
||||
int curGen = pop.getGeneration();
|
||||
MutateESRankMuCMA rcmaMute = null;
|
||||
if (pop.getEAIndividual(0).getMutationOperator() instanceof MutateESRankMuCMA) {
|
||||
rcmaMute = (MutateESRankMuCMA)pop.getEAIndividual(0).getMutationOperator();
|
||||
}
|
||||
|
||||
// stop if the range of the best fitness of the last 10 + flor(30 n /lambda) generations is zero
|
||||
// or if the range of these values and all fit values of the recent generation is below Tolfun = 10^-12
|
||||
//// interpret it a bit differently using FitnessConvergenceTerminator
|
||||
if (fitConvTerm.isTerminated(new SolutionSet(pop))) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (rcmaMute != null) {
|
||||
// stop if the std dev of the normal distribution is smaller than TolX in all coords
|
||||
// and sigma p_c is smaller than TolX in all components; TolX = 10^-12 sigma_0
|
||||
|
||||
if (rcmaMute.testAllDistBelow(10e-12*rcmaMute.getFirstSigma())) return true;
|
||||
|
||||
// stop if adding a 0.1 std dev vector in a principal axis dir. of C does not change <x>_w^g
|
||||
if (rcmaMute.testNoChangeAddingDevAxis(0.1, curGen)) return true;
|
||||
|
||||
// stop if adding a 0.2 std dev in each coordinate does (not???) change <x>_w^g
|
||||
if (rcmaMute.testNoEffectCoord(0.2)) return true;
|
||||
|
||||
// stop if the condition number of C exceeds 10^14
|
||||
if (rcmaMute.testCCondition(10e14)) return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the current population and a set of best individuals found (best current
|
||||
* and best single ones before
|
||||
* reinitializing the population after boosting the population size).
|
||||
*
|
||||
* @return A solution set of the current population and possibly earlier solutions
|
||||
*/
|
||||
public SolutionSet getAllSolutions() {
|
||||
Population sols = getPopulation().cloneWithoutInds();
|
||||
if (bestList != null) sols.addAll(bestList);
|
||||
if (best != null) sols.add(best);
|
||||
else sols.add(getPopulation().getBestEAIndividual());
|
||||
|
||||
SolutionSet solSet = new SolutionSet(getPopulation(), sols);
|
||||
return solSet;
|
||||
}
|
||||
|
||||
public void registerPopulationStateChanged(Object source, String name) {
|
||||
if (name.equals(Population.funCallIntervalReached)) {
|
||||
getPopulation().SetFunctionCalls(((Population)source).getFunctionCalls()); // TODO this is ugly
|
||||
super.firePropertyChangedEvent(name);
|
||||
} else {
|
||||
// System.err.println("Not forwarding event " + name);
|
||||
}
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return "ES-IPOP";
|
||||
}
|
||||
|
||||
public String globalInfo() {
|
||||
return "An ES with increasing population size.";
|
||||
}
|
||||
|
||||
/** Set an initial population size (if smaller lambda this is ignored).
|
||||
* @param l The inital population size.
|
||||
*/
|
||||
public void setInitialLambda(int l) {
|
||||
initialLambda = l;
|
||||
if (initialLambda < getMu()) setMu((initialLambda/2)+1);
|
||||
}
|
||||
|
||||
public int getInitialLambda() {
|
||||
return initialLambda;
|
||||
}
|
||||
|
||||
public String initialLambdaTipText() {
|
||||
return "Set the initial population size (lambda); mu should be about lambda/2";
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the incPopSizeFact
|
||||
*/
|
||||
public double getIncPopSizeFact() {
|
||||
return incPopSizeFact;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param incPopSizeFact the incPopSizeFact to set
|
||||
*/
|
||||
public void setIncPopSizeFact(double incPopSizeFact) {
|
||||
this.incPopSizeFact = incPopSizeFact;
|
||||
}
|
||||
|
||||
public String incPopSizeFactTipText() {
|
||||
return "Factor by which to increase lambda for each restart event, default is 2.";
|
||||
}
|
||||
}
|
@ -58,9 +58,11 @@ public class EvolutionaryProgramming implements InterfaceOptimizer, java.io.Seri
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
|
@ -67,10 +67,12 @@ public class FloodAlgorithm implements InterfaceOptimizer, java.io.Serializable
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
this.m_CurrentFloodPeak = this.m_InitialFloodPeak;
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
|
||||
/** This method will optimize
|
||||
|
@ -3,6 +3,7 @@ package eva2.server.go.strategies;
|
||||
import eva2.server.go.InterfacePopulationChangedEventListener;
|
||||
import eva2.server.go.individuals.AbstractEAIndividual;
|
||||
import eva2.server.go.individuals.GAIndividualBinaryData;
|
||||
import eva2.server.go.operators.mutation.InterfaceMutationGenerational;
|
||||
import eva2.server.go.operators.selection.InterfaceSelection;
|
||||
import eva2.server.go.operators.selection.SelectTournament;
|
||||
import eva2.server.go.populations.InterfaceSolutionSet;
|
||||
@ -66,9 +67,11 @@ public class GeneticAlgorithm implements InterfaceOptimizer, java.io.Serializabl
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
@ -110,6 +113,10 @@ public class GeneticAlgorithm implements InterfaceOptimizer, java.io.Serializabl
|
||||
parents = this.m_ParentSelection.selectFrom(this.m_Population, this.m_Population.getPopulationSize());
|
||||
//System.out.println("Parents:"+parents.getSolutionRepresentationFor());
|
||||
|
||||
if (parents.getEAIndividual(0).getMutationOperator() instanceof InterfaceMutationGenerational) {
|
||||
((InterfaceMutationGenerational)parents.getEAIndividual(0).getMutationOperator()).adaptAfterSelection(m_Population, parents);
|
||||
}
|
||||
|
||||
for (int i = 0; i < parents.size(); i++) {
|
||||
tmpIndy = ((AbstractEAIndividual)parents.get(i));
|
||||
if (tmpIndy == null) System.out.println("Individual null " + i + " Population size: "+ parents.size());
|
||||
@ -121,13 +128,18 @@ public class GeneticAlgorithm implements InterfaceOptimizer, java.io.Serializabl
|
||||
}
|
||||
result.add(i, offSprings[0]);
|
||||
}
|
||||
this.evaluatePopulation(result);
|
||||
|
||||
if (parents.getEAIndividual(0).getMutationOperator() instanceof InterfaceMutationGenerational) {
|
||||
((InterfaceMutationGenerational)parents.getEAIndividual(0).getMutationOperator()).adaptGenerational(m_Population, parents, result, true);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public void optimize() {
|
||||
Population nextGeneration;
|
||||
nextGeneration = this.generateChildren();
|
||||
this.evaluatePopulation(nextGeneration);
|
||||
|
||||
if (this.m_UseElitism) {
|
||||
AbstractEAIndividual elite = this.m_Population.getBestEAIndividual();
|
||||
if (elite != null) {
|
||||
|
@ -53,9 +53,11 @@ public class GradientDescentAlgorithm implements InterfaceOptimizer, java.io.Ser
|
||||
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.setPopulation((Population) pop.clone());
|
||||
if (reset) this.getPopulation().init();
|
||||
this.m_Problem.evaluate(this.getPopulation());
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.getPopulation().init();
|
||||
this.m_Problem.evaluate(this.getPopulation());
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
//System.out.println("initByPopulation() called");
|
||||
indyhash = new Hashtable();
|
||||
}
|
||||
|
@ -58,15 +58,13 @@ public class HillClimbing implements InterfaceOptimizer, java.io.Serializable {
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
|
||||
/** This method will init the optimizer with a given population
|
||||
* @param pop The initial population
|
||||
* @param reset If true the population is reset.
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will optimize
|
||||
|
@ -38,9 +38,11 @@ public interface InterfaceOptimizer {
|
||||
*/
|
||||
public void init();
|
||||
|
||||
/** This method will init the optimizer with a given population
|
||||
/**
|
||||
* This method will init the optimizer with a given population.
|
||||
*
|
||||
* @param pop The initial population
|
||||
* @param reset If true the population is reset.
|
||||
* @param reset If true the population is reinitialized and reevaluated.
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset);
|
||||
|
||||
@ -66,7 +68,7 @@ public interface InterfaceOptimizer {
|
||||
* May return the the same set as getPopulation if the optimizer makes no distinction, i.e. does
|
||||
* not collect solutions outside the current population.
|
||||
*
|
||||
* @return A population of found solutions.
|
||||
* @return A solution set of the current population and possibly earlier solutions.
|
||||
*/
|
||||
public InterfaceSolutionSet getAllSolutions();
|
||||
|
||||
|
@ -142,6 +142,7 @@ public class IslandModelEA implements InterfacePopulationChangedEventListener, I
|
||||
* @param reset If true the population is reset.
|
||||
*/
|
||||
public void initByPopulation(Population tpop, boolean reset) {
|
||||
// TODO this is again evil copy&paste style
|
||||
if (this.m_Show) {
|
||||
if (this.m_Plot == null) {
|
||||
double[] tmpD = new double[2];
|
||||
@ -152,8 +153,10 @@ public class IslandModelEA implements InterfacePopulationChangedEventListener, I
|
||||
}
|
||||
|
||||
this.m_Population = (Population)tpop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Population.incrGeneration();
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Population.incrGeneration();
|
||||
}
|
||||
this.m_Optimizer.init();
|
||||
this.m_Optimizer.SetProblem(this.m_Problem);
|
||||
InterfacePopulationChangedEventListener myLocal = null;
|
||||
|
@ -89,9 +89,11 @@ public class MemeticAlgorithm implements InterfaceOptimizer,
|
||||
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.setPopulation((Population) pop.clone());
|
||||
if (reset) this.getPopulation().init();
|
||||
this.m_Problem.evaluate(this.getPopulation());
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.getPopulation().init();
|
||||
this.m_Problem.evaluate(this.getPopulation());
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
public void init() {
|
||||
|
@ -64,9 +64,11 @@ public class MonteCarloSearch implements InterfaceOptimizer, java.io.Serializabl
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will optimize
|
||||
|
@ -85,9 +85,11 @@ public class ParticleFilterOptimization implements InterfaceOptimizer, java.io.S
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
|
@ -372,7 +372,7 @@ public class ParticleSwarmOptimization implements InterfaceOptimizer, java.io.Se
|
||||
indy.SetData(indexKey, i);
|
||||
indy.setIndividualIndex(i);
|
||||
}
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
if (reset) this.evaluatePopulation(this.m_Population);
|
||||
|
||||
for (int i = 0; i < this.m_Population.size(); i++) {
|
||||
indy = (AbstractEAIndividual) this.m_Population.get(i);
|
||||
@ -382,7 +382,7 @@ public class ParticleSwarmOptimization implements InterfaceOptimizer, java.io.Se
|
||||
}
|
||||
|
||||
this.m_BestIndividual = (AbstractEAIndividual)this.m_Population.getBestEAIndividual().clone();
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
|
||||
treeLevels = 0;
|
||||
// the HPSO tree will contain layers 0...HPSOLevels, the last one is "incomplete" with only HPSOOrphans number of nodes
|
||||
|
@ -72,10 +72,12 @@ public class PopulationBasedIncrementalLearning implements InterfaceOptimizer, j
|
||||
System.err.println("Error: PBIL only works with GAIndividuals!");
|
||||
}
|
||||
this.m_Population = new PBILPopulation();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Population.addPopulation((Population)pop.clone());
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
}
|
||||
((PBILPopulation)this.m_Population).buildProbabilityVector();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
|
||||
|
@ -67,10 +67,12 @@ public class SimulatedAnnealing implements InterfaceOptimizer, java.io.Serializa
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.m_CurrentTemperature = this.m_InitialTemperature;
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will optimize
|
||||
|
@ -62,9 +62,11 @@ public class SteadyStateGA implements InterfaceOptimizer, java.io.Serializable {
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.evaluatePopulation(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will evaluate the current population using the
|
||||
|
@ -65,10 +65,12 @@ public class ThresholdAlgorithm implements InterfaceOptimizer, java.io.Serializa
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
this.m_Population = (Population)pop.clone();
|
||||
if (reset) this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.m_CurrentT = this.m_InitialT;
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
if (reset) {
|
||||
this.m_Population.init();
|
||||
this.m_Problem.evaluate(this.m_Population);
|
||||
this.firePropertyChangedEvent("NextGenerationPerformed");
|
||||
}
|
||||
}
|
||||
|
||||
/** This method will optimize
|
||||
|
@ -240,6 +240,11 @@ public class Tribes implements InterfaceOptimizer, java.io.Serializable {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* As TRIBES manages an own structured set of particles (the list of Tribes containing explorers
|
||||
* and memories), the setPopulation method is only telling Tribes the range
|
||||
* of the indiviuals in the beginning of the run, the individuals will be discarded.
|
||||
*/
|
||||
public void initByPopulation(Population pop, boolean reset) {
|
||||
setPopulation(pop);
|
||||
}
|
||||
|
@ -675,4 +675,16 @@ public class Mathematics {
|
||||
}
|
||||
return A;
|
||||
}
|
||||
|
||||
public static double max(double[] vals) {
|
||||
double maxVal = vals[0];
|
||||
for (int i=1; i<vals.length; i++) maxVal = Math.max(maxVal, vals[i]);
|
||||
return maxVal;
|
||||
}
|
||||
|
||||
public static double min(double[] vals) {
|
||||
double minVal = vals[0];
|
||||
for (int i=1; i<vals.length; i++) minVal = Math.min(minVal, vals[i]);
|
||||
return minVal;
|
||||
}
|
||||
}
|
||||
|
@ -9,9 +9,9 @@ import java.text.DecimalFormatSymbols;
|
||||
import java.text.NumberFormat;
|
||||
import java.util.Locale;
|
||||
|
||||
import eva2.gui.BeanInspector;
|
||||
|
||||
import wsi.ra.math.Jama.util.Maths;
|
||||
import eva2.gui.BeanInspector;
|
||||
import eva2.tools.Pair;
|
||||
|
||||
|
||||
/**
|
||||
@ -260,6 +260,17 @@ public class Matrix implements Cloneable, java.io.Serializable {
|
||||
return vals;
|
||||
}
|
||||
|
||||
/** Copy a column from the matrix.
|
||||
@return Matrix elements packed in a one-dimensional array by columns.
|
||||
*/
|
||||
public double[] getColumn(int k) {
|
||||
double[] vals = new double[m];
|
||||
for (int i = 0; i < m; i++) {
|
||||
vals[i] = A[i][k];
|
||||
}
|
||||
return vals;
|
||||
}
|
||||
|
||||
/** Make a one-dimensional row packed copy of the internal array.
|
||||
@return Matrix elements packed in a one-dimensional array by rows.
|
||||
*/
|
||||
@ -764,6 +775,34 @@ public class Matrix implements Cloneable, java.io.Serializable {
|
||||
return X;
|
||||
}
|
||||
|
||||
/** Multiply a matrix by a vector, returning A*v.
|
||||
*
|
||||
@param v vector
|
||||
@return result vector
|
||||
*/
|
||||
public double[] times (double[] v) {
|
||||
// m: no rows
|
||||
double[] result = new double[m];
|
||||
times(v, result);
|
||||
return result;
|
||||
}
|
||||
|
||||
/** Multiply a matrix by a vector in place, result=A*v.
|
||||
*
|
||||
@param v vector
|
||||
@param result
|
||||
@return result vector
|
||||
*/
|
||||
public void times (double[] v, double[] result) {
|
||||
// m: no rows
|
||||
for (int i = 0; i < m; i++) {
|
||||
result[i] = 0;
|
||||
for (int j = 0; j < n; j++) {
|
||||
result[i] += get(i,j)*v[j];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
StringBuffer sb = new StringBuffer();
|
||||
for (int i=0; i<m; i++) {
|
||||
@ -976,6 +1015,25 @@ public class Matrix implements Cloneable, java.io.Serializable {
|
||||
return A;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the minimum and maximum value on the diagonal
|
||||
* as a pair.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
public Pair<Double,Double> getMinMaxDiag() {
|
||||
if (m<1 || n<1) return null;
|
||||
|
||||
double v = get(0,0);
|
||||
Pair<Double,Double> ret = new Pair<Double,Double>(v,v);
|
||||
for (int i=1; i<Math.min(m,n); i++) {
|
||||
v = get(i,i);
|
||||
ret.head = Math.min(ret.head, v);
|
||||
ret.tail = Math.max(ret.tail, v);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/** Print the matrix to stdout. Line the elements up in columns
|
||||
* with a Fortran-like 'Fw.d' style format.
|
||||
|
Loading…
x
Reference in New Issue
Block a user