Julia is moderately bad at dealing with global variables: Performance Tips · The Julia Language. The solution is to not use a global variable and put the code inside a function. With
function main()
i = 0
while i < 1000000
println(i)
i += 1
end
return i
end
@time main()
I get
8.606004 seconds (8.10 M allocations: 253.779 MiB, 0.43% gc time, 0.28% compilation time)
However with Julia v1.8 it’s possible to get non-horribly-slow global variables by type-annotating them. Now, with
i::Int = 0
@time while i < 1000000
println(i)
global i += 1
end
I get
8.125404 seconds (9.09 M allocations: 261.307 MiB, 0.48% gc time, 0.46% compilation time)
And if you remove side effects from the function, like printing to screen, then you get real optimisation:
julia> function main()
i = 0
while i < 1000000
# println(i)
i += 1
end
return i
end
main (generic function with 1 method)
julia> @code_llvm main()
; @ REPL[6]:1 within `main`
define i64 @julia_main_225() #0 {
top:
; @ REPL[6]:7 within `main`
ret i64 1000000
}
julia> @code_native main()
.text
; ┌ @ REPL[6]:7 within `main`
movl $1000000, %eax # imm = 0xF4240
retq
nopw %cs:(%rax,%rax)
; └
The compiler computes the result of this function at compile-time, and it automatically returns a constant.