I have a function f() = Int[]
.
Let’s try and check how much it allocates using @timev
(or @time
) and @allocations
.
julia> @timev f()
0.000002 seconds (1 allocation: 64 bytes)
elapsed time (ns): 1667
gc time (ns): 0
bytes allocated: 64
pool allocs: 1
non-pool GC allocs: 0
minor collections: 0
full collections: 0
Int64[]
julia> @allocations f()
0
See the “pool allocs” bit in the result from @timev
. I think @allocations
is supposed to count it too. But I was getting different number of allocations.
You can also try:
@timev Array{Int64}(undef)
@allocations Array{Int64}(undef)
@timev Core.Box()
@allocations Core.Box()
@timev Ref{Int64}()
@allocations Ref{Int64}()
So I complained here: `@allocated` and `@allocations` are giving the wrong result. · Issue #56705 · JuliaLang/julia · GitHub
I got the response:
@time returns the result. @allocated does not, so the system didn’t need to allocate it.
The same “does not return” logic applies to @allocations
according to its documentation, so I will stick to it as an example.
Why should @allocations
tell me that f()
or Array{Int64}(undef)
does not allocate?
This is the definition of @allocations
:
macro allocations(ex)
quote
Experimental.@force_compile
local stats = Base.gc_num()
$(esc(ex))
local diff = Base.GC_Diff(Base.gc_num(), stats)
Base.gc_alloc_count(diff)
end
end
I created two alternative versions, but this time. @alloc1
returns only the number of allocations, just like @allocations
, but @alloc2
returns the return value of f()
as well:
macro allocs1(ex)
quote
Base.Experimental.@force_compile
local stats = Base.gc_num()
local val = $(esc(ex))
local diff = Base.GC_Diff(Base.gc_num(), stats)
local count = Base.gc_alloc_count(diff)
(count,)
end
end
macro allocs2(ex)
quote
Base.Experimental.@force_compile
local stats = Base.gc_num()
local val = $(esc(ex))
local diff = Base.GC_Diff(Base.gc_num(), stats)
local count = Base.gc_alloc_count(diff)
(count, val)
end
end
@allocs1 f()
gives the same result as @allocations f()
, but @allocs2 f()
does not. Is this right? Is Julia shuffling the order of execution?