Hi I am working on the pi example in JuliaBox. When I am generating random numbers the only way I do not get 0 as the value of pi is if I multiply by rand() (as it did in the solution to the exercise). It looks like multiplying rand() makes x and y decimals. I was wondering how multiplying rand() was used or what it specifically does?
Acircle = 0
for i in 1:N
x, y = rand([-1, 1])*rand(), rand([-1, 1])*rand()
dist = sqrt(x^2 + y^2)
dist < r ? Acircle += 1 : Acircle += 0
N = 10000
r = 1
for what i see, rand(Vector) gives an random element of the vector, and rand([-1,1]) is either -1 or 1, so that operation is to give the x and y coordinates a random sign
You could also express something comparable as
2*rand()-1 — it’s just extending the range of generated values such that it covers the entire unit circle instead of just the upper right quadrant.
That said, the formula works just as well if you use
x, y = rand(), rand()! That just looks at the upper right quadrant, but it works because you’re symmetrically reducing the areas of the circle and the square by the same fraction.
If you care about performance, you should absolutely drop the
rand([-1, 1]). It makes no difference to the result, and it makes your code almost 10x slower. Most of that is due to the vectors
[-1, 1] you keep creating over and over, if you keep the
rands but replace them with
rand((-1, 1)) instead, you get a very large speed-up, since tuples are so efficient.
But, even so, just drop them entirely.
You can also get some improvement if you realize that
sqrt(x^2 + y^2) < r
is equivalent to
x^2 + y^2 < r^2 # and here you could just pre-calculate r^2
No need to calculate the
Furthermore, you can add a
Bool to an
Int. Doesn’t seem to matter much to performance, but it’s more elegant, imo:
Acircle += (x^2 + y^2 < r^2)
If you care even more about performance, there’s no need to actually store
function calc_pi(N, r)
Acirc = 0
for i in 1:N
Acirc += rand()^2 + rand()^2 < r^2
4Acirc / N
@btime on those:
julia> @btime calculate_pi(10^4, 1)
972.581 μs (20000 allocations: 1.83 MiB)
julia> @btime calc_pi(10^4, 1)
53.120 μs (0 allocations: 0 bytes)
Assigning something to a local variable is just giving it a name. It has no effect on how/where the value is stored or on performance.
@stevengj Eh… I checked again and you’re right. Good to know!
I guess it saves a few keystrokes though