|
|
|
@@ -1,13 +1,18 @@
|
|
|
|
|
package eva2.tools.math;
|
|
|
|
|
|
|
|
|
|
import java.util.ArrayList;
|
|
|
|
|
import java.util.Arrays;
|
|
|
|
|
import java.util.Random;
|
|
|
|
|
|
|
|
|
|
import eva2.tools.EVAHELP;
|
|
|
|
|
import eva2.tools.Mathematics;
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public class RNG extends Random {
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
private static final long serialVersionUID = 1565216859128723844L;
|
|
|
|
|
private static Random random;
|
|
|
|
|
private static long randomSeed;
|
|
|
|
|
/**
|
|
|
|
@@ -17,14 +22,17 @@ public class RNG extends Random {
|
|
|
|
|
randomSeed = System.currentTimeMillis();
|
|
|
|
|
random = new Random(randomSeed);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public static void setRandomSeed(long new_seed) {
|
|
|
|
|
// counter++;
|
|
|
|
|
randomSeed = new_seed;
|
|
|
|
|
if (randomSeed == 0) setRandomSeed();
|
|
|
|
|
else random = new Random(randomSeed);
|
|
|
|
|
if (randomSeed == 0)
|
|
|
|
|
setRandomSeed();
|
|
|
|
|
else
|
|
|
|
|
random = new Random(randomSeed);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
@@ -34,6 +42,7 @@ public class RNG extends Random {
|
|
|
|
|
randomSeed = new_seed;
|
|
|
|
|
random.setSeed(randomSeed);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -41,12 +50,14 @@ public class RNG extends Random {
|
|
|
|
|
randomSeed = System.currentTimeMillis();
|
|
|
|
|
random = new Random(randomSeed);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public static void setRandom(Random base_random) {
|
|
|
|
|
random = base_random;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -62,18 +73,23 @@ public class RNG extends Random {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Returns an evenly distributes int value between zero and
|
|
|
|
|
* upperLim-1.
|
|
|
|
|
* @param upperLim upper exclusive limit of the random int
|
|
|
|
|
* Returns an evenly distributes int value between zero and upperLim-1.
|
|
|
|
|
*
|
|
|
|
|
* @param upperLim
|
|
|
|
|
* upper exclusive limit of the random int
|
|
|
|
|
*/
|
|
|
|
|
public static int randomInt(int upperLim) {
|
|
|
|
|
return randomInt(0, upperLim - 1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/** This method returns a evenly distributed int value.
|
|
|
|
|
* The boundarys are included.
|
|
|
|
|
* @param lo Lower bound.
|
|
|
|
|
* @param hi Upper bound.
|
|
|
|
|
/**
|
|
|
|
|
* This method returns a evenly distributed int value. The boundarys are
|
|
|
|
|
* included.
|
|
|
|
|
*
|
|
|
|
|
* @param lo
|
|
|
|
|
* Lower bound.
|
|
|
|
|
* @param hi
|
|
|
|
|
* Upper bound.
|
|
|
|
|
* @return int
|
|
|
|
|
*/
|
|
|
|
|
public static int randomInt(int lo, int hi) {
|
|
|
|
@@ -83,26 +99,33 @@ public class RNG extends Random {
|
|
|
|
|
}
|
|
|
|
|
int result = (Math.abs(random.nextInt()) % (hi - lo + 1)) + lo;
|
|
|
|
|
if ((result < lo) || (result > hi)) {
|
|
|
|
|
System.err.println("Error, invalid value " + result + " in RNG.randomInt! boundaries were lo/hi: " + lo + " / " + hi);
|
|
|
|
|
System.err.println("Error, invalid value " + result
|
|
|
|
|
+ " in RNG.randomInt! boundaries were lo/hi: " + lo + " / "
|
|
|
|
|
+ hi);
|
|
|
|
|
result = Math.abs(random.nextInt() % (hi - lo + 1)) + lo;
|
|
|
|
|
}
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/** This method returns a random permutation of n int values
|
|
|
|
|
* @param length The number of int values
|
|
|
|
|
/**
|
|
|
|
|
* This method returns a random permutation of n int values
|
|
|
|
|
*
|
|
|
|
|
* @param length
|
|
|
|
|
* The number of int values
|
|
|
|
|
* @return The permutation [0-length-1]
|
|
|
|
|
*/
|
|
|
|
|
public static int[] randomPermutation(int length) {
|
|
|
|
|
boolean[] validList = new boolean[length];
|
|
|
|
|
int[] result = new int[length];
|
|
|
|
|
int index;
|
|
|
|
|
for (int i = 0; i < validList.length; i++) validList[i] = true;
|
|
|
|
|
for (int i = 0; i < validList.length; i++)
|
|
|
|
|
validList[i] = true;
|
|
|
|
|
for (int i = 0; i < result.length; i++) {
|
|
|
|
|
index = randomInt(0, length - 1);
|
|
|
|
|
while (!validList[index]) {
|
|
|
|
|
index++;
|
|
|
|
|
if (index == length) index = 0;
|
|
|
|
|
if (index == length)
|
|
|
|
|
index = 0;
|
|
|
|
|
}
|
|
|
|
|
validList[index] = false;
|
|
|
|
|
result[i] = index;
|
|
|
|
@@ -110,8 +133,11 @@ public class RNG extends Random {
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/** This method returns a random permutation of n int values
|
|
|
|
|
* @param length The number of int values
|
|
|
|
|
/**
|
|
|
|
|
* This method returns a random permutation of n int values
|
|
|
|
|
*
|
|
|
|
|
* @param length
|
|
|
|
|
* The number of int values
|
|
|
|
|
* @return The permutation [0-length-1]
|
|
|
|
|
*/
|
|
|
|
|
public static int[] randomPerm(int length) {
|
|
|
|
@@ -126,7 +152,8 @@ public class RNG extends Random {
|
|
|
|
|
intList.remove(index);
|
|
|
|
|
|
|
|
|
|
}
|
|
|
|
|
if (intList.size()>1) System.err.println("Error in randomPerm!");
|
|
|
|
|
if (intList.size() > 1)
|
|
|
|
|
System.err.println("Error in randomPerm!");
|
|
|
|
|
result[length - 1] = intList.get(0);
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
@@ -144,24 +171,28 @@ public class RNG extends Random {
|
|
|
|
|
public static long randomLong(long lo, long hi) {
|
|
|
|
|
return (Math.abs(random.nextLong()) % (hi - lo + 1)) + lo;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public static float randomFloat() {
|
|
|
|
|
return random.nextFloat();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public static float randomFloat(float lo, float hi) {
|
|
|
|
|
return (hi - lo) * random.nextFloat() + lo;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* A random double value between 0 and 1.
|
|
|
|
|
*/
|
|
|
|
|
public static double randomDouble() {
|
|
|
|
|
return random.nextDouble();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -185,19 +216,22 @@ public class RNG extends Random {
|
|
|
|
|
public static double[] randomDoubleArray(double[][] range) {
|
|
|
|
|
double[] xin = new double[range.length];
|
|
|
|
|
for (int i = 0; i < xin.length; i++)
|
|
|
|
|
xin[i] = (range[i][1]-range[i][0])*random.nextDouble()+range[i][0];
|
|
|
|
|
xin[i] = (range[i][1] - range[i][0]) * random.nextDouble()
|
|
|
|
|
+ range[i][0];
|
|
|
|
|
return xin;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Create a uniform random double vector within the given bounds (inclusive) in every dimension.
|
|
|
|
|
* Create a uniform random double vector within the given bounds (inclusive)
|
|
|
|
|
* in every dimension.
|
|
|
|
|
*
|
|
|
|
|
* @param lower
|
|
|
|
|
* @param upper
|
|
|
|
|
* @param size
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
public static double[] randomDoubleArray(double lower, double upper, int size) {
|
|
|
|
|
public static double[] randomDoubleArray(double lower, double upper,
|
|
|
|
|
int size) {
|
|
|
|
|
double[] result = new double[size];
|
|
|
|
|
for (int i = 0; i < result.length; i++) {
|
|
|
|
|
result[i] = RNG.randomDouble(lower, upper);
|
|
|
|
@@ -212,7 +246,8 @@ public class RNG extends Random {
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
|
public static double[] randomDoubleArray(double[] lo,double[] hi,double[] xin) {
|
|
|
|
|
public static double[] randomDoubleArray(double[] lo, double[] hi,
|
|
|
|
|
double[] xin) {
|
|
|
|
|
// counter++;
|
|
|
|
|
for (int i = 0; i < lo.length; i++)
|
|
|
|
|
xin[i] = (hi[i] - lo[i]) * random.nextDouble() + lo[i];
|
|
|
|
@@ -220,7 +255,8 @@ public class RNG extends Random {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Create a uniform random integer vector within the given bounds (inclusive) in every dimension.
|
|
|
|
|
* Create a uniform random integer vector within the given bounds
|
|
|
|
|
* (inclusive) in every dimension.
|
|
|
|
|
*
|
|
|
|
|
* @param n
|
|
|
|
|
* @param lower
|
|
|
|
@@ -242,6 +278,7 @@ public class RNG extends Random {
|
|
|
|
|
// counter++;
|
|
|
|
|
return (randomInt() == 1);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -260,6 +297,7 @@ public class RNG extends Random {
|
|
|
|
|
// counter++;
|
|
|
|
|
return (randomDouble() < p ? true : false);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -267,16 +305,19 @@ public class RNG extends Random {
|
|
|
|
|
// counter++;
|
|
|
|
|
return (float) random.nextGaussian() * dev;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Return a Gaussian double with mean 0 and deviation dev.
|
|
|
|
|
*
|
|
|
|
|
* @param dev the deviation of the distribution.
|
|
|
|
|
* @param dev
|
|
|
|
|
* the deviation of the distribution.
|
|
|
|
|
* @return a Gaussian double with mean 0 and given deviation.
|
|
|
|
|
*/
|
|
|
|
|
public static double gaussianDouble(double dev) {
|
|
|
|
|
// counter++;
|
|
|
|
|
return random.nextGaussian() * dev;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -284,6 +325,7 @@ public class RNG extends Random {
|
|
|
|
|
// counter++;
|
|
|
|
|
return (float) (-mean * Math.log(randomDouble()));
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
*
|
|
|
|
|
*/
|
|
|
|
@@ -293,20 +335,23 @@ public class RNG extends Random {
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Returns a vector denoting a random point around the center
|
|
|
|
|
* - inside a hypersphere of uniform distribution if nonUnif=0,
|
|
|
|
|
* - inside a hypersphere of non-uniform distribution if nonUnif > 0,
|
|
|
|
|
* - inside a D-Gaussian if nonUnif < 0.
|
|
|
|
|
* For case 2, the nonUnif parameter is used as standard deviation (instead of 1/D), the parameter
|
|
|
|
|
* is not further used in the other two cases.
|
|
|
|
|
* Original code by Maurice Clerc, from the TRIBES package
|
|
|
|
|
* Returns a vector denoting a random point around the center - inside a
|
|
|
|
|
* hypersphere of uniform distribution if nonUnif=0, - inside a hypersphere
|
|
|
|
|
* of non-uniform distribution if nonUnif > 0, - inside a D-Gaussian if
|
|
|
|
|
* nonUnif < 0. For case 2, the nonUnif parameter is used as standard
|
|
|
|
|
* deviation (instead of 1/D), the parameter is not further used in the
|
|
|
|
|
* other two cases. Original code by Maurice Clerc, from the TRIBES package
|
|
|
|
|
*
|
|
|
|
|
* @param center center point of the distribution
|
|
|
|
|
* @param radius radius of the distribution
|
|
|
|
|
* @param nonUnif kind of distribution
|
|
|
|
|
* @param center
|
|
|
|
|
* center point of the distribution
|
|
|
|
|
* @param radius
|
|
|
|
|
* radius of the distribution
|
|
|
|
|
* @param nonUnif
|
|
|
|
|
* kind of distribution
|
|
|
|
|
*
|
|
|
|
|
**/
|
|
|
|
|
public static double[] randHypersphere(double[] center, double radius, double nonUnif) {
|
|
|
|
|
public static double[] randHypersphere(double[] center, double radius,
|
|
|
|
|
double nonUnif) {
|
|
|
|
|
double[] x = new double[center.length];
|
|
|
|
|
int j;
|
|
|
|
|
double xLen, r;
|
|
|
|
@@ -325,9 +370,12 @@ public class RNG extends Random {
|
|
|
|
|
// ----------------------------------- Step 2. Random radius
|
|
|
|
|
|
|
|
|
|
r = randomDouble();
|
|
|
|
|
if (nonUnif < 0) r = gaussianDouble(r/2); // D-Gaussian
|
|
|
|
|
else if (nonUnif > 0) r = Math.pow(r,nonUnif); // non-uniform hypersphere
|
|
|
|
|
else r=Math.pow(r,1./D); // Real hypersphere
|
|
|
|
|
if (nonUnif < 0)
|
|
|
|
|
r = gaussianDouble(r / 2); // D-Gaussian
|
|
|
|
|
else if (nonUnif > 0)
|
|
|
|
|
r = Math.pow(r, nonUnif); // non-uniform hypersphere
|
|
|
|
|
else
|
|
|
|
|
r = Math.pow(r, 1. / D); // Real hypersphere
|
|
|
|
|
|
|
|
|
|
for (j = 0; j < D; j++) {
|
|
|
|
|
x[j] = center[j] + radius * r * x[j] / xLen;
|
|
|
|
@@ -337,8 +385,11 @@ public class RNG extends Random {
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Adds Gaussian noise to a double vector
|
|
|
|
|
* @param v the double vector
|
|
|
|
|
* @param dev the Gaussian deviation
|
|
|
|
|
*
|
|
|
|
|
* @param v
|
|
|
|
|
* the double vector
|
|
|
|
|
* @param dev
|
|
|
|
|
* the Gaussian deviation
|
|
|
|
|
*/
|
|
|
|
|
public static void addNoise(double[] v, double dev) {
|
|
|
|
|
for (int i = 0; i < v.length; i++) {
|
|
|
|
@@ -366,15 +417,16 @@ public class RNG extends Random {
|
|
|
|
|
* @param n
|
|
|
|
|
* @return
|
|
|
|
|
*/
|
|
|
|
|
public static double[] gaussianVector(double dev, double[] result, boolean normalize) {
|
|
|
|
|
public static double[] gaussianVector(double dev, double[] result,
|
|
|
|
|
boolean normalize) {
|
|
|
|
|
for (int i = 0; i < result.length; i++) {
|
|
|
|
|
result[i] = RNG.gaussianDouble(dev);
|
|
|
|
|
}
|
|
|
|
|
if (normalize) Mathematics.normVect(result, result);
|
|
|
|
|
if (normalize)
|
|
|
|
|
Mathematics.normVect(result, result);
|
|
|
|
|
return result;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// public static int testRndInt(long seed, int bits) {
|
|
|
|
|
// return (int)(seed >>> (48 - bits));
|
|
|
|
|
// }
|
|
|
|
@@ -386,8 +438,10 @@ public class RNG extends Random {
|
|
|
|
|
// }
|
|
|
|
|
// int result = (Math.abs(testRndInt(seed,32))%(hi-lo+1))+lo;
|
|
|
|
|
// if ((result < lo) || (result > hi)) {
|
|
|
|
|
// System.err.println("Error, invalid value " + result + " in RNG.randomInt! boundaries were lo/hi: " + lo + " / " + hi);
|
|
|
|
|
// System.out.println("Error, invalid value " + result + " in RNG.randomInt! boundaries were lo/hi: " + lo + " / " + hi);
|
|
|
|
|
// System.err.println("Error, invalid value " + result +
|
|
|
|
|
// " in RNG.randomInt! boundaries were lo/hi: " + lo + " / " + hi);
|
|
|
|
|
// System.out.println("Error, invalid value " + result +
|
|
|
|
|
// " in RNG.randomInt! boundaries were lo/hi: " + lo + " / " + hi);
|
|
|
|
|
// }
|
|
|
|
|
// return result;
|
|
|
|
|
// }
|
|
|
|
@@ -411,7 +465,8 @@ public class RNG extends Random {
|
|
|
|
|
// }
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Create a uniform random double vector within the given bounds (inclusive) in every dimension.
|
|
|
|
|
* Create a uniform random double vector within the given bounds (inclusive)
|
|
|
|
|
* in every dimension.
|
|
|
|
|
*
|
|
|
|
|
* @param n
|
|
|
|
|
* @param lower
|
|
|
|
@@ -425,5 +480,4 @@ public class RNG extends Random {
|
|
|
|
|
// }
|
|
|
|
|
// return result;
|
|
|
|
|
// }
|
|
|
|
|
|
|
|
|
|
}
|