tags:

views:

20466

answers:

5

In Ruby, how do you generate a random number between 0 and n? In .NET you can create a Random object, does something like this exist for Ruby?

+1  A: 

Well, I figured it out. Apparently there is a builtin (?) function called rand:

rand(n + 1)

If someone answers with a more detailed answer, I'll mark that as the correct answer.

Mark A. Nicolosi
Yes, it's builtin in the Kernel module.
Christoph Schiessl
Ahh, thanks Chrisoph.
Mark A. Nicolosi
+35  A: 

What is wrong with rand(range) ?

If you needed a random integer to simulate a roll of a six-sided die, you'd use: 1 + rand(6). A roll in craps could be simulated with 2 + rand(6) + rand(6).

Finally, if you just need a random float, just call rand with no arguments.

(From first result of google search: Ruby Random Numbers)


As Marc-André Lafortune mentions in his answer below (go upvote it), Ruby1.9.2 has its own Random class (that Marc-André himself helped to debug, hence the 1.9.2 target for that feature).

For instance, in this game where you need to guess 10 numbers, you can initialize them with:

10.times.map{ Random.new.rand(20..30) } 
#=> [26, 26, 22, 20, 30, 26, 23, 23, 25, 22]
VonC
Thanks, VonC. I eventually did google for the answer, but I looked here for and didn't find the answer, so I thought it might be a useful addition. That's the purpose of SO, right?
Mark A. Nicolosi
No problem, you have SO perfectly figured ;)
VonC
Yup, SO is just a place for people too lazy to use google.
Justin
What's funny is that this post is now the first Google result.
ahsteele
Isn't this terribly non-ruby-like? I thought everything is an object, least-surprise and that...
Yar
@yar: It is a bit "perlish". Now Ruby has it's Random class (see my answer)
Marc-André Lafortune
+1  A: 

Don't forget to seed the RNG with srand() first.

Liebach
What happens if you don't call srand()?
Alex B
srand is automatically called with the seed being from the current time if it wasn't already called.
Julian
+2  A: 

Apparently srand is called when the ruby interpreter is started.

Therefore unless you have a specific need to reset the seed - extra calls to srand are unnecessary.

waldo
+20  A: 

Ruby 1.9.2 introduces the Random class, so while you can still use rand, you can now create your own random number generator object. It can be marshaled, among other things.

r = Random.new(42)
r.rand(0...100) # => 51

Available for all versions of Ruby by requiring my backports gem.

Marc-André Lafortune
Excellent! +1. I have completed my own answer to reflect that new feature (and mentioning your contribution with Bug #3104 ;) ).
VonC
How does the `backports` gem work, in broad strokes?
Yar
@yar: My `backports` gem is simply a collection of methods that are new to RUby 1.8.7, 1.9.1, 1.9.2, but implemented in Ruby. I use RubySpec to insure that the results are compatible with Ruby.
Marc-André Lafortune
@Marc-André Lafortune, thanks for that. It's always been strange to me how much of Ruby is implemented in non-Ruby (C or whatever) due to speed requirements. But them's the breaks
Yar
@yar: Until there is a really good implementation of Ruby, the builtin Random class will perform much better than my compatible Ruby version... It's the goal of Rubinius to minimize the C++ code without a big loss of performance.
Marc-André Lafortune
@Marc-André Lafortune, while we're here: is JRuby not a good implementation? I could be totally off-base and you'll say, "no it's the worst of all."
Yar
@yar: It is! But the mersenne twister in Ruby will spend most of the time in function calls and very little time doing the basic calculations. By a good implementation, I meant one that could inline those dynamic calls very well (which I don't think the JVM can do). Rubinius aims to do that. I haven't done any performance testing, though, so I'm speculating :-)
Marc-André Lafortune
Rubinius, eh? I'll keep my eye on that one, I see it's right in line with what we're talking about. Fascinating in any case... thanks for the chat.
Yar