In the Julia language, how are function compilations reused?

Viewed 116

I'm toying around with Julia, and I have run into a question about the compiler/JIT compilation scheme that Julia uses. If I write a function such as

function f(x) 
  return mapreduce(*,+,x,x)
end

Then since this function works on abstract arrays, its shape can't be known until it's used, so it can't be compiled. Then if use this in a function, g, whose inputs are arrays of arrays of floats like so:

function g(y) 
  return mapreduce(f,+,y)
end

Or alternatively

function g2(y) 
  res = 0 
  for x in y 
    res = res + f(x)
  end
  return res 
end 

Then, when we use g, say g([[1,2],[3,4]]), eventually f will be called. Say it's called on [1,2] first. Then it's compiled, and evaluated. As far as I can tell, since f([3,4]) is on the exact same type as f([1,2]), f will be reused (since the inputs are both 2 dimensional arrays of numbers). However, when I type @code_llvm(f([1,2])) and @code_llvm(f([3,4])) I see that the names of the functions are different (they do have a common prefix, something like julia_f_ and then its followed by a number). Also, if I call @code_llvm(f([1,2])) again, I get yet another name.

Does Julia indeed allow g to reuse the compiled version of f for each application? Does this depend on the length of the arrays involved; i.e. in g([w1,...,wn]) does each wi have to have the same length for f to be reused?

1 Answers

I don't know much about Julia internals, but perhaps this provides some evidence that f is only compiled once:

function f(x) 
    mapreduce(*, +, x, x)
end

function g(y) 
    mapreduce(f, +, y)
end
julia> @time g([[1, 2], [3, 4]])
  0.099061 seconds (322.72 k allocations: 19.687 MiB, 99.94% compilation time)
30

julia> @time g([[1, 2], [3, 4]])
  0.000021 seconds (11 allocations: 672 bytes)
30

The first time g is run, 99.94% of the time is spent on compilation. The second time g is run, 0% of the time is spent on compilation. Note that you need Julia v1.6+ if you want to get the compilation time from the @time macro.

Related