# Can I efficiently use a compiled function as an input to another compiled function?

I have a compiled function(such as $$f\left(z,c\right)=z^2+c$$) which will get replaced by different equations as the code runs. I'm using this compiled function(#1) inside another compiled function(#2).

I don't want to recompile #2 every time #1 is changed though. I know I can just dump #1 in #2 declaration like any other function, such as Sin[], and it'll work. It'll just wrap #1 in a MainEvaluate like MainEvaluate[Hold[func1][C1]]. #1 is intended to be a listable function BTW.

I know MainEvaluate can be inefficient though, so I was wondering if I could do this more efficiently. I was thinking a dynamically updating library could do it, but I have no clue how to do that, or if that's the case. Does anyone more knowledgeable about Compile have any advice?

From docs, Compile can handle _Integer, _Real, _Complex and True|False, i.e. you can't pass a function as an argument.

But you can do this using new framework with Typed and FunctionCompile.

(* version = 12.2 *)
fn = Function[
{
Typed[x,"Real64"],
Typed[f, {"Real64"} -> "Real64"]
},
Block[
{y},
y = f[x] ;
y^2
]
] ;

cf = FunctionCompile[fn] ;

f = FunctionCompile[Function[{Typed[x, "Real64"]}, Sin[x]]] ;
g = FunctionCompile[Function[{Typed[x, "Real64"]}, Cos[x]]] ;

cf[1.0, f]
cf[1.0, g]

• I did notice that FunctionCompile had the capacity to take CompiledCodeFunctions as inputs, however it seems too limited. You don't seem to be able to tell FunctionCompile you want the function to be listable, nor will FunctionCompile accept CompiledFunctions(which can be listable) as inputs. I don't even think FunctionCompile has the error handling functionality of Compile when it comes to replacing overflowed values, which is necessary for escape time fractals. FunctionCompile seems too experimental/underdocumented currently to be useful. Mar 10 at 16:16
• Right, FunctionCompile still needs some dev. I'm not sure you can avoid recompilation with Compile, but to remove MainEvaluate call use CompilationOptions->{InlineExternalDefinitions->True}. Since you care only about overflows, you can handled them manually and set "RuntimeOptions" -> "Speed".
– I.M.
Mar 11 at 5:09
• You can also try using LibraryLink and wrap lib functions with Compile to get listability
– I.M.
Mar 11 at 5:10
• Well ideally I wouldn't have to recompile #2 ever. Dealing with a MainEvaluate would be preferable to that. Also, apparently there's no way to make Mathematica ignore complex number overflow. Also, the function I'm using can apparently overflow in 2 different ways which have extremely different meanings, so I seem to have to rely on Evaluate as a fallback for RuntimeErrorHandler, rather than a mere list. I could try to recode it entirely out of real numbers, but I'm not sure it's a good idea. Mar 11 at 15:51
• If what you mentioned regarding LibraryLink would make it so #2 wouldn't need to be recompiled, remove the associated MainEvaluate, and keep #1 listable, could you edit your answer on how to correctly implement it? Mar 11 at 15:51