# Function array performance

I have an array of functions that each return a float, and so I am trying to assign the results of those functions to an array. So I had something like this

``````results = similar(f_arr, Float64)
results .= [f(a, b, c) for f in f_arr]
``````

however this is 10+ times slower than manually calling each function in the array, as in

``````results = similar(f_arr, Float64)
results = f1(a, b, c)
results = f2(a, b, c)
...
``````

Is there an explanation as to why the first way is so slow? I also tried something like the following

``````results = similar(f_arr, Float64)
results .= [f_arr[i](a, b, c) for i in 1:length(f_arr)]
``````

and I got an error because the tuple `(a, b, c)` was getting passed to `f_arr[i]` instead of passing all three variables in the first two code blocks. I am fairly new to Julia so maybe there is some piece of documentation I am missing, and I would love to be pointed in the right direction.

1 Like

Functions all have their own type so this code isn’t type stable.

1 Like

You might be able to get some improvement by using a tuple instead.

``````using BenchmarkTools

f_array = [sin,cos,tan]
f_tuple = (sin,cos,tan)

x = 1.0

@btime [f(\$x) for f in f_array];

@btime [f(\$x) for f in f_tuple];
``````

354.717 ns (11 allocations: 272 bytes)
189.819 ns (3 allocations: 112 bytes)

1 Like

This turns a tuple into an array, which is not optimal. Try to keep it as a tuple:

``````1.7.2> @btime ((f,x)->f(x)).(\$f, \$x)
29.435 ns (0 allocations: 0 bytes)
(0.8414709848078965, 0.5403023058681398, 1.5574077246549023)
``````
4 Likes

Same as yours but a bit more elegant:

``````julia> @btime map(f->f(\$x), \$f)
34.945 ns (0 allocations: 0 bytes)
(0.8414709848078965, 0.5403023058681398, 1.5574077246549023)
``````
1 Like

What is the context for this? Maybe there is a more idiomatic way to represent what you are trying to do.

2 Likes