ngmf.util.cosu.luca.SCE Maven / Gradle / Ivy
package ngmf.util.cosu.luca;
import java.io.PrintStream;
import java.util.Arrays;
import java.util.Collections;
import java.util.Vector;
import oms3.dsl.cosu.Step;
/**
*/
public class SCE {
double[] initialParameterSet; //INITIAL PARAMETER SET
double[] lowerBound; //LOWER BOUND ON PARAMETERS
double[] upperBound; // UPPER BOUND ON PARAMETERS
int numOfParams; // NUMBER OF PARAMETERS TO BE OPTIMIZED
int initNumOfComplexes; // NUMBER OF COMPLEXES IN THE INITIAL POPULATION
int numOfPointsInComplex; // NUMBER OF POINTS IN EACH COMPLEX
int initTotalNumOfPoints; //(initTotalNumOfPoints = initNumOfComplexes * numOfPointsInComplex
//TOTAL NUMBER OF POINTS IN INITIAL POPULATION (NPT=NGS*NPG)
int numOfPointsInSubComplex; //NUMBER OF POINTS IN A SUB-COMPLEX
int numOfEvolutionSteps; //NUMBER OF EVOLUTION STEPS ALLOWED FOR EACH COMPLEX BEFORE
//COMPLEX SHUFFLING
int minNumOfComplexes; //MINIMUM NUMBER OF COMPLEXES REQUIRED, IF THE NUMBER OF
//COMPLEXES IS ALLOWED TO REDUCE AS THE OPTIMIZATION PROCEEDS
//ISEED = INITIAL RANDOM SEED
//INIFLG = FLAG ON WHETHER TO INCLUDE THE INITIAL POINT IN POPULATION
// = 0, NOT INCLUDED
//= 1, INCLUDED
boolean includeInitialPOINT;
//CONVERGENCE CHECK PARAMETERS
//MAXN = MAX NO. OF TRIALS ALLOWED BEFORE OPTIMIZATION IS TERMINATED
int maxNumOfTrials;
// NUMBER OF SHUFFLING LOOPS IN WHICH THE CRITERION VALUE MUST
// CHANGE BY THE GIVEN PERCENTAGE BEFORE OPTIMIZATION IS TERMINATED
int numOfShufflingLoops;
//PERCENTAGE BY WHICH THE CRITERION VALUE MUST CHANGE IN
// GIVEN NUMBER OF SHUFFLING LOOPS
double percentage;
// FLAG INDICATING WHETHER PARAMETER CONVERGENCE IS REACHED
boolean paramConvergenceSATISFIED;
//COORDINATES OF POINTS IN THE POPULATION
double[][] pointsX;
//FUNCTION VALUES OF X(.,.)
double[] objFuncValueOfX;
//COORDINATES OF A SINGLE POINT IN X
double[] pointInX;
//COORDINATES OF POINTS IN A COMPLEX
double[][] pointsInComplex;
//FUNCTION VALUES OF CX(.,.)
double[] objFuncValuesOfComplex;
//COORDINATES OF POINTS IN THE CURRENT SIMPLEX
double[][] pointsInSimplex;
//FUNCTION VALUES OF S(.,.)
double[] objFuncValuesOfSimplex;
//WORST POINT AT CURRENT SHUFFLING LOOP
double[] worstPoint;
//FUNCTION VALUE OF WORSTX(.)
double objFuncValueOfWorstPoint;
//STANDARD DEVIATION OF PARAMETERS IN THE POPULATION
double[] stdDevOfPopulation;
//NORMALIZED GEOMETRIC MEAN OF PARAMETER RANGES
double normalizedGeometricMean;
//INDICES LOCATING POSITION OF S(.,.) IN X(.,.)
int[] indicesOfSimplex;
//BOUND ON ITH VARIABLE BEING OPTIMIZED
double[] bound;
//NUMBER OF COMPLEXES IN CURRENT POPULATION
int currentNumOfComplexes;
//NUMBER OF COMPLEXES IN LAST POPULATION
int lastNumOfComplexes;
double[] bestCriterion;
int totalNumOfPoints; // the number of points in current population
double[] initialPoint; // initial point == initialParameterSet
//
private ExecutionHandle executionHandle;
Step stepData;
Step.Data data;
int NLOOP = 0;
int LOOP = 0;
int IGS = 0;
int icall = 0;
//
PrintStream out = System.out;
public SCE(ExecutionHandle executionHandle, Step stepData, Step.Data data) {
this.executionHandle = executionHandle;
this.stepData = stepData; // stepData contains data needed for running SCE
this.data = data;
// get values
numOfParams = stepData.params().getCount();
initNumOfComplexes = stepData.getInitComplexes();
numOfPointsInComplex = stepData.getPointsPerComplex();
numOfPointsInSubComplex = stepData.getPointsPerSubcomplex();
numOfEvolutionSteps = stepData.getEvolutions();
minNumOfComplexes = stepData.getMinComplexes();
includeInitialPOINT = true;
maxNumOfTrials = stepData.getMaxExec();
numOfShufflingLoops = stepData.getShufflingLoops();
percentage = stepData.getOfPercentage();
upperBound = data.getUpperBound();
lowerBound = data.getLowerBound();
initialParameterSet = data.getParamValues();
// System.out.println(maxNumOfTrials + " " + initNumOfComplexes + " " + numOfPointsInComplex + " " + numOfPointsInSubComplex + " " + numOfEvolutionSteps
// + " " + minNumOfComplexes + " " + numOfShufflingLoops + " " + percentage);
initTotalNumOfPoints = initNumOfComplexes * numOfPointsInComplex;
// initialize arrays
pointsX = new double[initTotalNumOfPoints][numOfParams];
objFuncValueOfX = new double[initTotalNumOfPoints];
pointInX = new double[numOfParams];
pointsInComplex = new double[numOfPointsInComplex][numOfParams];
objFuncValuesOfComplex = new double[numOfPointsInComplex];
pointsInSimplex = new double[numOfPointsInSubComplex][numOfParams];
objFuncValuesOfSimplex = new double[numOfPointsInSubComplex];
worstPoint = new double[numOfParams];
stdDevOfPopulation = new double[numOfParams];
indicesOfSimplex = new int[numOfPointsInSubComplex];
bound = new double[numOfParams];
bestCriterion = new double[10];
initialPoint = new double[numOfParams];
}
public void setOut(PrintStream out) {
this.out = out;
}
public void run() throws Exception {
currentNumOfComplexes = initNumOfComplexes;
totalNumOfPoints = initTotalNumOfPoints;
double objFuncValue;
for (int j = 0; j < numOfParams; j++) {
bound[j] = upperBound[j] - lowerBound[j];
initialPoint[j] = initialParameterSet[j];
}
objFuncValue = execute(initialPoint); // write initialPoint in the 'newPARAMS' file, executes runMMS and SRobjfun()
out.println("\n Initial OF value : " + objFuncValue);
out.print(" Initial Parameterset : ");
for (int j = 0; j < initialParameterSet.length; j++) {
out.print(" " + initialParameterSet[j]);
}
out.println();
if (maxNumOfTrials <= 1) {
out.println("Due to max model execution of 1, no optimization was done. " +
"The only thing that was done is the calculation of objective function for initial values.");
return; // done with this method
}
out.println(" SCE generating data points ....");
if (includeInitialPOINT) {
// out.println("Initial point will be included");
for (int j = 0; j < numOfParams; j++) {
pointsX[0][j] = initialParameterSet[j];
}
objFuncValueOfX[0] = objFuncValue;
} else {
// out.println("Initial point won't be included");
for (int j = 0; j < numOfParams; j++) {
pointsX[0][j] = lowerBound[j] + bound[j] * Math.random();
pointInX[j] = pointsX[0][j];
}
// write pointInX in the 'newPARAMS' file, executes runMMS and SRobjfun()
objFuncValue = execute(pointInX);
objFuncValueOfX[0] = objFuncValue;
}
data.setObjFuncValueOfBestPoint(objFuncValueOfX[0]);
int outputType = 1;
if (icall < maxNumOfTrials) {
for (int i = 1; i < totalNumOfPoints; i++) {
for (int j = 0; j < numOfParams; j++) {
pointsX[i][j] = lowerBound[j] + bound[j] * Math.random();
pointInX[j] = pointsX[i][j];
}
objFuncValueOfX[i] = execute(pointInX);
//ICALL++;
if (icall >= maxNumOfTrials) {
totalNumOfPoints = i + 1;
pointsX = copy(pointsX, totalNumOfPoints);
objFuncValueOfX = copy(objFuncValueOfX, totalNumOfPoints);
break;
}
}
// out.println("size of pointsX = " + totalNumOfPoints + " (max size is " + pointsX.length + ")" +
// ", max size of objFuncValueOfX = " + objFuncValueOfX.length);
sort_duan(pointsX, objFuncValueOfX);
// set the best point and its objective function value
data.setBestParamData(pointsX[0], objFuncValueOfX[0]);
for (int j = 0; j < numOfParams; j++) {
worstPoint[j] = pointsX[totalNumOfPoints - 1][j];
}
objFuncValueOfWorstPoint = objFuncValueOfX[totalNumOfPoints - 1];
parstt();
// double distribution = normdistForBestPoint();
out.print("\n Results of the initial SCE research:");
// out.println("NLOOP: " + NLOOP);
// out.println("ICALL: " + icall);
// out.println("Number of complexes in current population: " + currentNumOfComplexes);
// out.println("Function value of best point: " + data.getObjFuncValueOfBestPoint());
// out.println("Function value of worst point: " + objFuncValueOfWorstPoint);
// out.println("DIST for best point (DIST(0)): " + distribution);
// out.println("Best point at current shuffling loop");
for (int j = 0; j < numOfParams; j++) {
out.print(" " + pointsX[0][j]); // display the best point
}
out.println();
if (icall >= maxNumOfTrials) {
outputType = 1;
} else if (paramConvergenceSATISFIED) {
outputType = 3;
} else {
outputType = mainLoop();
}
}
/*************************************************************************
* Creating a parameter file that contains the best point. This is not done
* in the original SCE code.
**************************************************************************/
// get the best point
double[] bestPoint = data.getBestParamDataArray();
data.setParamValues(bestPoint); // set the best point in stepData
executionHandle.writeParameterFile(data);
String output = "";
out.println("\n **************************************************");
if (outputType == 1) {
output = " Optimization terminated, limit " +
"on the maximum number of trials, " + maxNumOfTrials + ", was exceeded.\n" +
" Search was stopped at sub-complex " + (LOOP + 1) + " of complex " + (IGS + 1) +
" in shuffling loop. " + NLOOP;// + "\n" +
} else if (outputType == 2) {
// double percentage2 = percentage * 100;
output = " Optimization terminated, OF value " +
"has not changed " + percentage + "% in " + numOfShufflingLoops +
" shuffling loops.";
} else if (outputType == 3) {
double normalizedGeometricMean2 = normalizedGeometricMean * 100;
output = " Optimization terminated, population has " +
"converged into " + normalizedGeometricMean2 + "% of the feasible space.";
} else if (outputType == 4) {
output = " SCE was stopped.";
}
out.println(output);
out.println(" **************************************************");
out.print(" Final parameter estimates:");
for (int j = 0; j < numOfParams; j++) {
out.print(" " + bestPoint[j]);
initialParameterSet[j] = bestPoint[j];
}
out.println();
out.println(" Final OF value: " + data.getObjFuncValueOfBestPoint());
}
// MAIN LOOP
private int mainLoop() throws Exception {
out.println(" SCE shuffling ....");
int outputType = 1; // different output will be displayed depending on the value of ouputTYpe
while (true) {
NLOOP++;
for (IGS = 0; IGS < currentNumOfComplexes; IGS++) {
for (int k1 = 0; k1 < numOfPointsInComplex; k1++) {
int k2 = k1 * currentNumOfComplexes + IGS;
for (int j = 0; j < numOfParams; j++) {
pointsInComplex[k1][j] = pointsX[k2][j];
}
objFuncValuesOfComplex[k1] = objFuncValueOfX[k2];
}
for (LOOP = 0; LOOP < numOfEvolutionSteps; LOOP++) {
if (numOfPointsInSubComplex == numOfPointsInComplex) {
for (int k = 0; k < numOfPointsInSubComplex; k++) {
indicesOfSimplex[k] = k;
}
} else {
// k = 0 instead of k = 1 because the line above (indicesOfSimplex[0] = ....)
// is removed.
for (int k = 0; k < numOfPointsInSubComplex; k++) {
boolean again = true;
int lpos = -1;
while (again) {
again = false;
lpos = (int) (numOfPointsInComplex + 0.5 -
Math.sqrt(Math.pow((numOfPointsInComplex + 0.5), 2) -
numOfPointsInComplex * (numOfPointsInComplex + 1) * Math.random()));
// check if any element from indicesOfSimplex[0] to indicesOfSimplex[k-1]
// is equal to LPOS. If not, get out of the for loop, finish the while(AGAIN) loop,
// and set LPOS as a value of indicesOfSimplex[k]
for (int k1 = 0; k1 < k; k1++) {
if (lpos == indicesOfSimplex[k1]) {
again = true;
break;
}
}
}
indicesOfSimplex[k] = lpos;
}
// sort the indiciesOfSimplex array in increasing order
Arrays.sort(indicesOfSimplex);
}
for (int k = 0; k < numOfPointsInSubComplex; k++) {
for (int j = 0; j < numOfParams; j++) {
pointsInSimplex[k][j] = pointsInComplex[indicesOfSimplex[k]][j];
}
objFuncValuesOfSimplex[k] = objFuncValuesOfComplex[indicesOfSimplex[k]];
}
cce();
for (int k = 0; k < numOfPointsInSubComplex; k++) {
for (int j = 0; j < numOfParams; j++) {
pointsInComplex[indicesOfSimplex[k]][j] = pointsInSimplex[k][j];
}
objFuncValuesOfComplex[indicesOfSimplex[k]] = objFuncValuesOfSimplex[k];
}
sort_duan(pointsInComplex, objFuncValuesOfComplex);
if (icall >= maxNumOfTrials) {
break;
}
} // end of loop with LOOP
for (int k1 = 0; k1 < numOfPointsInComplex; k1++) {
int k2 = k1 * currentNumOfComplexes + IGS;
for (int j = 0; j < numOfParams; j++) {
pointsX[k2][j] = pointsInComplex[k1][j];
}
objFuncValueOfX[k2] = objFuncValuesOfComplex[k1];
}
if (icall >= maxNumOfTrials) {
break;
}
} // end of for loop with IGS
sort_duan(pointsX, objFuncValueOfX);
// set the best point and its objective function value
data.setBestParamData(pointsX[0], objFuncValueOfX[0]);
for (int j = 0; j < numOfParams; j++) {
worstPoint[j] = pointsX[totalNumOfPoints - 1][j];
}
objFuncValueOfWorstPoint = objFuncValueOfX[totalNumOfPoints - 1];
parstt();
// double distribution = normdistForBestPoint();
// out.println("loop " + NLOOP + " ICALL = " + icall);
// out.println("Number of complexes in a current population: " + currentNumOfComplexes);
// out.println("Objective Function value of best point: " + data.getObjFuncValueOfBestPoint());
// out.println("Objective Function value of worst point: " + objFuncValueOfWorstPoint);
// out.println("Normal Distribution of best point: " + distribution);
// out.println();
if (icall >= maxNumOfTrials) {
outputType = 1;
break;
}
int lastIndex = bestCriterion.length - 1; // currently this value is 9
bestCriterion[lastIndex] = data.getObjFuncValueOfBestPoint();
if (NLOOP > numOfShufflingLoops) // ### Is this right?
{
// This condition is needed. If NLOOP < vectorOfBestCriterion.length,
// then there are some elements that are not set yet in vectorOfBestCriterion.
if (NLOOP >= bestCriterion.length) {
int idx = lastIndex - numOfShufflingLoops;
if (idx < 0) //#### For now, tempIndex is set to 0 if tempIndex < 0. This line should be changed.
{
idx = 0;
}
double denomi = Math.abs(bestCriterion[idx] + bestCriterion[lastIndex]) / 2;
double timeou = Math.abs(bestCriterion[idx] - bestCriterion[lastIndex]) / denomi;
// out.println("\n$$$$$$$$$$$$ NLOOP = " + NLOOP + "\tnumOfShufflingLoops = " + numOfShufflingLoops +
// "\tvectorOfBestCriterion length = " + bestCriterion.length + "\tPercentage is calculated: " + timeou);
if (timeou < percentage) {
outputType = 2;
break;
}
}
}
for (int l = 0; l < lastIndex; l++) {
bestCriterion[l] = bestCriterion[l + 1]; // ######## Does this work????
}
if (paramConvergenceSATISFIED) {
outputType = 3;
break;
}
if (currentNumOfComplexes > minNumOfComplexes) {
lastNumOfComplexes = currentNumOfComplexes;
currentNumOfComplexes -= 1;
totalNumOfPoints = currentNumOfComplexes * numOfPointsInComplex;
comp();
}
}
return outputType;
}
//#########################################################################
//## Other functions
//########################################################################
double execute(double[] array) throws Exception {
data.setParamValues(array);
executionHandle.execute(data);
icall++;
double of = stepData.calculateObjectiveFunctionValue(executionHandle);
double distribution = normdistForBestPoint();
// out.println("loop " + NLOOP + " ICALL = " + icall);
// out.println("Number of complexes in a current population: " + currentNumOfComplexes);
// out.println("Objective Function value of best point: " + data.getObjFuncValueOfBestPoint());
// out.println("Objective Function value of worst point: " + objFuncValueOfWorstPoint);
// out.println("Normal Distribution of best point: " + distribution);
out.print(" %r " + icall + ": " + of + " [" + data.getObjFuncValueOfBestPoint() + "/" + objFuncValueOfWorstPoint+"]" + " c:" + currentNumOfComplexes + " d:" + distribution);
return of;
}
void sort_duan(double[][] x, double[] y) {
Vector indices = new Vector();
for (int i = 0; i < x.length; i++) {
indices.add(new Integer(i));
}
if (!stepData.maximizeObjectiveFunctionValue()) {
Sorter sorter = new Sorter(y, Sorter.ASCENDING);
Collections.sort(indices, sorter);
Arrays.sort(y);
} else {
Sorter sorter = new Sorter(y, Sorter.DESCENDING);
Collections.sort(indices, sorter);
// sort y[] in ascending order
Arrays.sort(y);
// reverse the order of y to be in descending order
double[] new_y = new double[y.length];
for (int i = 0; i < y.length; i++) {
new_y[i] = y[y.length - 1 - i];
}
for (int i = 0; i < y.length; i++) {
y[i] = new_y[i];
}
}
double[][] new_x = new double[x.length][x[0].length];
for (int i = 0; i < new_x.length; i++) {
new_x[i] = x[indices.get(i).intValue()];
}
for (int i = 0; i < x.length; i++) {
x[i] = new_x[i];
}
}
void parstt() {
double[] xMax = new double[numOfParams];
double[] xMin = new double[numOfParams];
double[] xMean = new double[numOfParams];
double delta = Math.pow(10, -20);
// double delta = 10E-20;
double peps = Math.pow(10, -3); // minimum standard deviation
// double peps = 10E-3; // minimum standard deviation
double gSum = 0;
for (int k = 0; k < numOfParams; k++) {
xMax[k] = Double.MIN_VALUE;
xMin[k] = Double.MAX_VALUE;
double xSum1 = 0;
double xSum2 = 0;
for (int i = 0; i < totalNumOfPoints; i++) {
xMax[k] = Math.max(pointsX[i][k], xMax[k]);
xMin[k] = Math.min(pointsX[i][k], xMin[k]);
xSum1 = xSum1 + pointsX[i][k];
xSum2 = xSum2 + pointsX[i][k] * pointsX[i][k];
}
xMean[k] = xSum1 / (double) totalNumOfPoints;
stdDevOfPopulation[k] = xSum2 / (double) totalNumOfPoints - xMean[k] * xMean[k];
if (stdDevOfPopulation[k] <= delta) {
stdDevOfPopulation[k] = delta;
}
stdDevOfPopulation[k] = Math.sqrt(stdDevOfPopulation[k]) / bound[k];
gSum += Math.log(delta + (xMax[k] - xMin[k]) / bound[k]);
}
normalizedGeometricMean = Math.pow(Math.E, gSum / (double) numOfParams);
paramConvergenceSATISFIED = false;
if (normalizedGeometricMean <= peps) {
paramConvergenceSATISFIED = true;
}
}
/* This method returns the normal distance of the best point. This method
* is used instead of normdist() because normdist() determins the normal
* distances for all points, which is not needed. */
double normdistForBestPoint() {
double normalDistance = 0;
for (int i = 0; i < numOfParams; i++) {
normalDistance += Math.abs(pointsX[0][i] - initialPoint[i]) / bound[i];
}
normalDistance = normalDistance / numOfParams;
return normalDistance;
}
void comp() {
double[][] tempPoints = new double[totalNumOfPoints][numOfParams];
double[] tempObjFuncValues = new double[totalNumOfPoints];
// copy selected elements in pointsX and objFuncValueOfX to tempPoints and tempObjFuncValues
for (int igs = 0; igs < currentNumOfComplexes; igs++) {
for (int ipg = 0; ipg < numOfPointsInComplex; ipg++) {
int k1 = ipg * lastNumOfComplexes + igs;
int k2 = ipg * currentNumOfComplexes + igs;
for (int i = 0; i < numOfParams; i++) {
tempPoints[k2][i] = pointsX[k1][i];
}
tempObjFuncValues[k2] = objFuncValueOfX[k1];
}
}
// reinitialize pointsX and objFuncValueOfX with a correct size
pointsX = new double[totalNumOfPoints][numOfParams];
objFuncValueOfX = new double[totalNumOfPoints];
// copy elements of tempPointx and tempObjFuncValues back to pointsX and objFuncValueOfX
for (int j = 0; j < totalNumOfPoints; j++) {
for (int i = 0; i < numOfParams; i++) {
pointsX[j][i] = tempPoints[j][i];
}
objFuncValueOfX[j] = tempObjFuncValues[j];
}
}
void cce() throws Exception {
double[] worstPointSimplex = new double[numOfParams]; // WO(.)
double[] centroid = new double[numOfParams]; //CE(.)
double[] newPoint = new double[numOfParams]; //SNEW(.)
double[] vector = new double[numOfParams]; //STEP(.)
double worstObjFuncValue; //FW
for (int j = 0; j < numOfParams; j++) {
// pointsInSimplex[] is sorted based on the objective functions values,
// so the element in the last index is the worst point.
worstPointSimplex[j] = pointsInSimplex[numOfPointsInSubComplex - 1][j];
centroid[j] = 0;
// exclude the last point (worst point) in this loop
for (int i = 0; i < (numOfPointsInSubComplex - 1); i++) {
centroid[j] += pointsInSimplex[i][j];
}
centroid[j] = centroid[j] / ((double) (numOfPointsInSubComplex - 1));
vector[j] = centroid[j] - worstPointSimplex[j];
}
worstObjFuncValue = objFuncValuesOfSimplex[numOfPointsInSubComplex - 1];
for (int j = 0; j < numOfParams; j++) {
newPoint[j] = worstPointSimplex[j] + 2 * vector[j];
}
boolean outOfBOUND = false;
for (int j = 0; j < numOfParams; j++) {
if ((newPoint[j] > upperBound[j]) || (newPoint[j] < lowerBound[j])) {
outOfBOUND = true;
break;
}
}
if (outOfBOUND) {
getNewPointAtRandom(newPoint);
}
double newObjFuncValue = execute(newPoint);
if ((stepData.maximizeObjectiveFunctionValue() && newObjFuncValue <= worstObjFuncValue) ||
(!stepData.maximizeObjectiveFunctionValue() && newObjFuncValue >= worstObjFuncValue)) {
if (icall >= maxNumOfTrials) {
return; //ICALL;
}
for (int j = 0; j < numOfParams; j++) {
newPoint[j] = worstPointSimplex[j] + 0.5 * vector[j];
}
newObjFuncValue = execute(newPoint);
if ((stepData.maximizeObjectiveFunctionValue() && newObjFuncValue < worstObjFuncValue) ||
(!stepData.maximizeObjectiveFunctionValue() && newObjFuncValue > worstObjFuncValue)) {
if (icall >= maxNumOfTrials) {
return;
}
getNewPointAtRandom(newPoint);
newObjFuncValue = execute(newPoint);
}// end of the 2nd if ((newObjFuncValue > worstObjFuncValue) ... )
} // end of the 1st if ((newObjFuncValue > worstObjFuncValue) ... )
for (int j = 0; j < numOfParams; j++) {
pointsInSimplex[numOfPointsInSubComplex - 1][j] = newPoint[j];
}
objFuncValuesOfSimplex[numOfPointsInSubComplex - 1] = newObjFuncValue;
}
/* a new point is assigned to newPoint based on stdDevOfPopulation[],
* gasdev(), bound[], and etc.*/
void getNewPointAtRandom(double[] newPoint) {
for (int j = 0; j < numOfParams; j++) {
int nnn = 0;
do {
double R = gasdev();
newPoint[j] = pointsInSimplex[0][j] + stdDevOfPopulation[j] * R * bound[j];
nnn++;
if (nnn == 1001) {
out.println("SCE: getNewPointAtRandom(): Having hard time generating a new point in a feasible region");
}
if (nnn > 1000) {
newPoint[j] = lowerBound[j] + Math.abs(R) * (0.5 * bound[j]);
if (nnn % 100 == 1) {
out.print("Attempt " + nnn + ": new point = " + newPoint[j] +
", lower bound = " + lowerBound[j] + ", upper bound = " + upperBound[j]);
}
if ((newPoint[j] > upperBound[j]) || (newPoint[j] < lowerBound[j])) {
out.println(" ---> out of bound");
} else {
out.println(" ---> in bound!!");
}
}
} while ((newPoint[j] > upperBound[j]) || (newPoint[j] < lowerBound[j]));
}
}
//
boolean calculateGASDEV = true; // if true, gasdev() returns gasdevValue1
double gasdevValue1; // one of the two values generated in gasdev()
double gasdevValue2; // one of the two values generated in gasdev()
/* returns a normally distributed deviate with zero mean and unit variance,
* using random number generator, as the source of uniform deviates.
*/
double gasdev() {
double R, v1, v2;
if (calculateGASDEV) {
// if we don't have an extra deviate handy
do {
// pick two uniform numbers in the square extending from -1 to +1
// in each direction
v1 = 2 * Math.random() - 1;
v2 = 2 * Math.random() - 1;
// check if v1 and v2 are in the unit circle
R = v1 * v1 + v2 * v2;
} while (R >= 1); // if v1 and v2 are not in the unit circle
// make the Box-Muller transformation to get two normal deviates
double fac = Math.sqrt((-1) * ((2 * Math.log(R)) / R));
gasdevValue2 = v1 * fac; // one of the two normal deviates. gasdevValue2 is returned
// next time this function is called
gasdevValue1 = v2 * fac; // the other normal deviate, which will be returned at this time
calculateGASDEV = false;
return gasdevValue1;
} else {
calculateGASDEV = true;
return gasdevValue2;
}
}
/* returns an array of the specified size, containing the elements of index
* from 0 to size - 1 in source. */
double[] copy(double[] source, int size) {
double[] newArray = new double[size];
for (int i = 0; i < size; i++) {
newArray[i] = source[i];
}
return newArray;
}
/* returns an 2D array[rowSize][length of columns of source], containing
* the elements from source[0][] to source[size-1][]. */
double[][] copy(double[][] source, int rowSize) {
double[][] newArray = new double[rowSize][source[0].length];
for (int i = 0; i < rowSize; i++) {
for (int j = 0; j < newArray[0].length; j++) {
newArray[i][j] = source[i][j];
}
}
return newArray;
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy