What is some code to generate normally distributed random numbers in ruby?
(Note: I answered my own question, but I'll wait a few days before accepting to see if anyone has a better answer.)
EDIT:
Searching for this, I looked at all pages on SO resulting from the two searches:
+"normal distribution" ruby
and
+gaussian +random ruby
In Ruby, there are many ways to generate random numbers with various properties. The rand method can be used in 3 ways: Without arguments, rand gives you a floating point number between 0 & 1 (like 0.4836732493) With an integer argument ( rand(10) ) you get a new integer between 0 & that number.
. A random variable with a Gaussian distribution is said to be normally distributed, and is called a normal deviate. Normal distributions are important in statistics and are often used in the natural and social sciences to represent real-valued random variables whose distributions are not known.
Ruby | Random rand() function Random#rand() : rand() is a Random class method which generates a random value. Syntax: Random.rand() Parameter: Random values. Return: generates a random value.
Python's random.gauss() and Boost's normal_distribution both use the Box-Muller transform, so that should be good enough for Ruby too.
def gaussian(mean, stddev, rand) theta = 2 * Math::PI * rand.call rho = Math.sqrt(-2 * Math.log(1 - rand.call)) scale = stddev * rho x = mean + scale * Math.cos(theta) y = mean + scale * Math.sin(theta) return x, y end
The method can be wrapped up in a class that returns the samples one by one.
class RandomGaussian def initialize(mean, stddev, rand_helper = lambda { Kernel.rand }) @rand_helper = rand_helper @mean = mean @stddev = stddev @valid = false @next = 0 end def rand if @valid then @valid = false return @next else @valid = true x, y = self.class.gaussian(@mean, @stddev, @rand_helper) @next = y return x end end private def self.gaussian(mean, stddev, rand) theta = 2 * Math::PI * rand.call rho = Math.sqrt(-2 * Math.log(1 - rand.call)) scale = stddev * rho x = mean + scale * Math.cos(theta) y = mean + scale * Math.sin(theta) return x, y end end
(CC0)
To the extent possible under law, antonakos has waived all copyright and related or neighboring rights to the RandomGaussian
Ruby class. This work is published from: Denmark.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With