5
$\begingroup$

Is it possible to compile while changing the value of the arguments the function receives, instead of just creating new variables, and then returning those new variables,i.e., is it possible to pass by reference? How do I do this?

As an example:

cf=Compile[{{mat1,_Real,3},{mat2,_Real,3}},

mat1=mat1+mat2;
mat2=mat2*2;

]

where mat1 and mat2 are matrices of dimension $3\times N$.

When trying to compile the function cf I get the error

Compile::argset: The assignment to mat1 is illegal; it is not valid to assign a value to an argument.

So, my question is how can I bypass this, and use pass by reference instead of pass by value?

$\endgroup$
5
  • 2
    $\begingroup$ Could you please elaborate more on what you are trying to do? Show an example of the function you want to compile, and the options you want to change. $\endgroup$
    – rhermans
    Commented Oct 20, 2014 at 17:05
  • $\begingroup$ @rhermans please check the edit. $\endgroup$ Commented Oct 20, 2014 at 18:12
  • $\begingroup$ @m_goldberg is this question still not clear? $\endgroup$ Commented Oct 20, 2014 at 21:52
  • 1
    $\begingroup$ +1 and a reopen for your update. This is the kind of additional thought and detail required for a good question. $\endgroup$
    – Mr.Wizard
    Commented Oct 21, 2014 at 1:33
  • $\begingroup$ @Mr.Wizard Thanks ;) $\endgroup$ Commented Oct 21, 2014 at 10:29

1 Answer 1

4
$\begingroup$

As far as I understand the concept there is no true pass-by-reference in Mathematica. Attempting to make assignments to arguments is in fact a common mistake which I addressed in this answer: Attempting to make an assignment to the argument of a function. As described there one needs a Hold attribute for in-place modification of definitions, e.g.:

SetAttributes[foo, HoldFirst]
foo[bar_, new_] := bar = {bar, new};

x = {1};
foo[x, 2];

x
{{1}, 2}

This requires passing a Symbol name which is not a type that is supported by Compile.
One can nevertheless make assignments to Symbols (through a callback to the main evaluator):

cf = Compile[{{mat1, _Real, 3}}, x = mat1; 1];

cf[{{{2}, {8}}}];

x
{{{2.}, {8.}}}

Since this is a main evaluator callback the assignment function exists verbatim in cf:

Cases[cf, _Function, -1, 1]
{Function[{mat1}, x = mat1]}

This means that you can actually replace that Symbol with a different one, e.g.:

(cf /. HoldPattern[x] :> q)[{{{4, 5, 6}}}]

q

x
{{{4., 5., 6.}}}

{{{2.}, {8.}}}

Note that x was not modified. This illustrates that you can write hybrid functions that are partially compiled and yet have assignments to passed-in Symbols. Whether or not this prove to be useful in practice remains to be seen. If this does seem to be what you are looking for I can develop this further.

$\endgroup$
1
  • $\begingroup$ I think the example you gave, with the callback to the main evaluator is enough for my case. The rest, I didn't seem to understand :/ I'll have to study what it means as soon as I get some free time. $\endgroup$ Commented Oct 21, 2014 at 20:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.