Reputation: 1727
I'm working on an image editor and I'm about to implement filters. I decided to go with some kind of blur or noise.
Anyway, I decided I wanted a uniform filter so I read up on Random.nextGaussian()
.
However, since I'm working with RGB values that range from 0 to 255. How can I scale this random double value to fit within 0 and 255?
The random value returned by the nextGaussian() can range from -1 to 1 I believe.
So, I want to preserve the relative difference between the random values. "Scale" or "move the number range" if that makes sense.
I know it's possible but I can't figure it out. Thanks in advance.
Essentially, I need it to be a number between 0 and 1.
Upvotes: 4
Views: 4320
Reputation: 71
You can fit Normal (Gaussian) distribution between ~[0,1] with adjusting mean and std. For example, use mean = 0.5, std = 0.15, and you will get value between [0,1] with total probability of 99.91%. In the end, you can ensure that value is strictly between [0,1].
Supplier<Double> alphaSupplier = new Supplier<Double>() {
@Override
public Double get() {
double value = new Random().nextGaussian() * 0.15 + 0.5;
return Math.max(0, Math.min(1, value));
}
};
double random value = alphaSupplier.get();
Upvotes: 1
Reputation: 1
You can use nextGaussian() with Math.abs() so that you can obtain positive values of Gaussian distribution.
Random random = new Random();
double positiveRandomValue = Math.abs(random.nextGaussian());
Upvotes: 0
Reputation: 476534
In that case you should use nextDouble()
.
The Gaussian distribution is a distribution that ranges over the entire collection of double values (mathematically speaking, from minus infinity to positive infinity) with a peak around zero. The Gaussian distribution is thus not uniform.
The nextDouble()
method draws numbers uniformly between 0
and 1
(0
included, 1
excluded).
You can thus draw a number randomly between 0
and 255
(both inclusive) using the following code:
Random rand = new Random();
int value = (int) math.floor(256.0*rand.nextDouble());
A faster algorithm is however masking a random integer (Random.nextInt
):
Random rand = new Random();
int value = rand.nextInt()&0xff;
This algorithm isn't faster in big-oh analysis, but it saves one the more expensive nextDouble
method call as well as a floating point multiplication and a float-to-int conversion.
Upvotes: 3