java stdrandom_StdRandom.java

/*************************************************************************

* Compilation: javac StdRandom.java

* Execution: java StdRandom

* Dependencies: StdOut.java

*

* A library of static methods to generate pseudo-random numbers from

* different distributions (bernoulli, uniform, gaussian, discrete,

* and exponential). Also includes a method for shuffling an array.

*

*

* % java StdRandom 5

* seed = 1316600602069

* 59 16.81826 true 8.83954 0

* 32 91.32098 true 9.11026 0

* 35 10.11874 true 8.95396 3

* 92 32.88401 true 8.87089 0

* 72 92.55791 true 9.46241 0

*

* % java StdRandom 5

* seed = 1316600616575

* 96 60.17070 true 8.72821 0

* 79 32.01607 true 8.58159 0

* 81 59.49065 true 9.10423 1

* 96 51.65818 true 9.02102 0

* 99 17.55771 true 8.99762 0

*

* % java StdRandom 5 1316600616575

* seed = 1316600616575

* 96 60.17070 true 8.72821 0

* 79 32.01607 true 8.58159 0

* 81 59.49065 true 9.10423 1

* 96 51.65818 true 9.02102 0

* 99 17.55771 true 8.99762 0

*

*

* Remark

* ------

* - Relies on randomness of nextDouble() method in java.util.Random

* to generate pseudorandom numbers in [0, 1).

*

* - This library allows you to set and get the pseudorandom number seed.

*

* - Seehttp://www.honeylocust.com/RngPack/for an industrial

* strength random number generator in Java.

*

*************************************************************************/

importjava.util.Random;/*** Standard random. This class provides methods for generating

* random number from various distributions.

*

* For additional documentation, see Section 2.2 of

* Introduction to Programming in Java: An Interdisciplinary Approach by Robert Sedgewick and Kevin Wayne.

*

*@authorRobert Sedgewick

*@authorKevin Wayne*/

public final classStdRandom {private static Random random; //pseudo-random number generator

private static long seed; //pseudo-random number generator seed//static initializer

static{//this is how the seed was set in Java 1.4

seed =System.currentTimeMillis();

random= newRandom(seed);

}//don't instantiate

privateStdRandom() { }/*** Sets the seed of the psedurandom number generator.*/

public static void setSeed(longs) {

seed=s;

random= newRandom(seed);

}/*** Returns the seed of the psedurandom number generator.*/

public static longgetSeed() {returnseed;

}/*** Return real number uniformly in [0, 1).*/

public static doubleuniform() {returnrandom.nextDouble();

}/*** Returns an integer uniformly between 0 (inclusive) and N (exclusive).

*@throwsIllegalArgumentException if N <= 0*/

public static int uniform(intN) {if (N <= 0) throw new IllegalArgumentException("Parameter N must be positive");returnrandom.nextInt(N);

}/STATIC METHODS BELOW RELY ON JAVA.UTIL.RANDOM ONLY INDIRECTLY VIA//THE STATIC METHODS ABOVE.

///

/*** Returns a real number uniformly in [0, 1).

*@deprecatedclearer to use {@link#uniform()}*/

public static doublerandom() {returnuniform();

}/*** Returns an integer uniformly in [a, b).

*@throwsIllegalArgumentException if b <= a

*@throwsIllegalArgumentException if b - a >= Integer.MAX_VALUE*/

public static int uniform(int a, intb) {if (b <= a) throw new IllegalArgumentException("Invalid range");if ((long) b - a >= Integer.MAX_VALUE) throw new IllegalArgumentException("Invalid range");return a + uniform(b -a);

}/*** Returns a real number uniformly in [a, b).

*@throwsIllegalArgumentException unless a < b*/

public static double uniform(double a, doubleb) {if (!(a < b)) throw new IllegalArgumentException("Invalid range");return a + uniform() * (b-a);

}/*** Returns a boolean, which is true with probability p, and false otherwise.

*@throwsIllegalArgumentException unless p >= 0.0 and p <= 1.0*/

public static boolean bernoulli(doublep) {if (!(p >= 0.0 && p <= 1.0))throw new IllegalArgumentException("Probability must be between 0.0 and 1.0");return uniform()

}/*** Returns a boolean, which is true with probability .5, and false otherwise.*/

public static booleanbernoulli() {return bernoulli(0.5);

}/*** Returns a real number with a standard Gaussian distribution.*/

public static doublegaussian() {//use the polar form of the Box-Muller transform

doubler, x, y;do{

x= uniform(-1.0, 1.0);

y= uniform(-1.0, 1.0);

r= x*x + y*y;

}while (r >= 1 || r == 0);return x * Math.sqrt(-2 * Math.log(r) /r);//Remark: y * Math.sqrt(-2 * Math.log(r) / r)//is an independent random gaussian

}/*** Returns a real number from a gaussian distribution with given mean and stddev*/

public static double gaussian(double mean, doublestddev) {return mean + stddev *gaussian();

}/*** Returns an integer with a geometric distribution with mean 1/p.

*@throwsIllegalArgumentException unless p >= 0.0 and p <= 1.0*/

public static int geometric(doublep) {if (!(p >= 0.0 && p <= 1.0))throw new IllegalArgumentException("Probability must be between 0.0 and 1.0");//using algorithm given by Knuth

return (int) Math.ceil(Math.log(uniform()) / Math.log(1.0 -p));

}/*** Return an integer with a Poisson distribution with mean lambda.

*@throwsIllegalArgumentException unless lambda > 0.0 and not infinite*/

public static int poisson(doublelambda) {if (!(lambda > 0.0))throw new IllegalArgumentException("Parameter lambda must be positive");if(Double.isInfinite(lambda))throw new IllegalArgumentException("Parameter lambda must not be infinite");//using algorithm given by Knuth//seehttp://en.wikipedia.org/wiki/Poisson_distribution

int k = 0;double p = 1.0;double L = Math.exp(-lambda);do{

k++;

p*=uniform();

}while (p >=L);return k-1;

}/*** Returns a real number with a Pareto distribution with parameter alpha.

*@throwsIllegalArgumentException unless alpha > 0.0*/

public static double pareto(doublealpha) {if (!(alpha > 0.0))throw new IllegalArgumentException("Shape parameter alpha must be positive");return Math.pow(1 - uniform(), -1.0/alpha) - 1.0;

}/*** Returns a real number with a Cauchy distribution.*/

public static doublecauchy() {return Math.tan(Math.PI * (uniform() - 0.5));

}/*** Returns a number from a discrete distribution: i with probability a[i].

* throws IllegalArgumentException if sum of array entries is not (very nearly) equal to 1.0

* throws IllegalArgumentException unless a[i] >= 0.0 for each index i*/

public static int discrete(double[] a) {double EPSILON = 1E-14;double sum = 0.0;for (int i = 0; i < a.length; i++) {if (!(a[i] >= 0.0)) throw new IllegalArgumentException("array entry " + i + " must be nonnegative: " +a[i]);

sum= sum +a[i];

}if (sum > 1.0 + EPSILON || sum < 1.0 -EPSILON)throw new IllegalArgumentException("sum of array entries does not approximately equal 1.0: " +sum);//the for loop may not return a value when both r is (nearly) 1.0 and when the//cumulative sum is less than 1.0 (as a result of floating-point roundoff error)

while (true) {double r =uniform();

sum= 0.0;for (int i = 0; i < a.length; i++) {

sum= sum +a[i];if (sum > r) returni;

}

}

}/*** Returns a real number from an exponential distribution with rate lambda.

*@throwsIllegalArgumentException unless lambda > 0.0*/

public static double exp(doublelambda) {if (!(lambda > 0.0))throw new IllegalArgumentException("Rate lambda must be positive");return -Math.log(1 - uniform()) /lambda;

}/*** Rearrange the elements of an array in random order.*/

public static voidshuffle(Object[] a) {int N =a.length;for (int i = 0; i < N; i++) {int r = i + uniform(N-i); //between i and N-1

Object temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Rearrange the elements of a double array in random order.*/

public static void shuffle(double[] a) {int N =a.length;for (int i = 0; i < N; i++) {int r = i + uniform(N-i); //between i and N-1

double temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Rearrange the elements of an int array in random order.*/

public static void shuffle(int[] a) {int N =a.length;for (int i = 0; i < N; i++) {int r = i + uniform(N-i); //between i and N-1

int temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Rearrange the elements of the subarray a[lo..hi] in random order.*/

public static void shuffle(Object[] a, int lo, inthi) {if (lo < 0 || lo > hi || hi >=a.length) {throw new IndexOutOfBoundsException("Illegal subarray range");

}for (int i = lo; i <= hi; i++) {int r = i + uniform(hi-i+1); //between i and hi

Object temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Rearrange the elements of the subarray a[lo..hi] in random order.*/

public static void shuffle(double[] a, int lo, inthi) {if (lo < 0 || lo > hi || hi >=a.length) {throw new IndexOutOfBoundsException("Illegal subarray range");

}for (int i = lo; i <= hi; i++) {int r = i + uniform(hi-i+1); //between i and hi

double temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Rearrange the elements of the subarray a[lo..hi] in random order.*/

public static void shuffle(int[] a, int lo, inthi) {if (lo < 0 || lo > hi || hi >=a.length) {throw new IndexOutOfBoundsException("Illegal subarray range");

}for (int i = lo; i <= hi; i++) {int r = i + uniform(hi-i+1); //between i and hi

int temp =a[i];

a[i]=a[r];

a[r]=temp;

}

}/*** Unit test.*/

public static voidmain(String[] args) {int N = Integer.parseInt(args[0]);if (args.length == 2) StdRandom.setSeed(Long.parseLong(args[1]));double[] t = { .5, .3, .1, .1};

StdOut.println("seed = " +StdRandom.getSeed());for (int i = 0; i < N; i++) {

StdOut.printf("%2d " , uniform(100));

StdOut.printf("%8.5f ", uniform(10.0, 99.0));

StdOut.printf("%5b " , bernoulli(.5));

StdOut.printf("%7.5f ", gaussian(9.0, .2));

StdOut.printf("%2d ", discrete(t));

StdOut.println();

}

String[] a= "A B C D E F G".split(" ");for(String s : a)

StdOut.print(s+ " ");

StdOut.println();

}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值