6
$\begingroup$

Woud there be an elegant way to use a held option ?

For example if I need to pass by reference several variables but I don't always need all of them, it can be useful. For example if I want to append an element to a List/Association/Dataset.

I've managed to make something work but it's not very usable.

l = {};
ClearAll@ffff;
Options[ffff] = {"a" -> Hold[l]};
ffff[x_, OptionsPattern[]] := Function[Null, AppendTo[#, x], HoldFirst] @@ OptionValue["a"];
ffff[2]
l
$\endgroup$
0

2 Answers 2

12
$\begingroup$

I'd do something like this:

l = {};
ClearAll@ffff;
Options[ffff] = {"a" :> l};
ffff[x_, OptionsPattern[]] := 
  OptionValue[Automatic, Automatic, "a", Function[v, AppendTo[v, x], HoldFirst]]

That is, use RuleDelayed instead of Rule to define your held option, and then use extended syntax of OptionValue.

$\endgroup$
1
  • 1
    $\begingroup$ Nice, I didn't know this fourth argument of OptionValue. $\endgroup$
    – faysou
    Nov 16, 2014 at 19:23
3
$\begingroup$

As an improvement to Leonid's answer I've added a helper function, to avoid the Function syntax everytime.

l={};
ClearAll@ffff;
Options[ffff]={"a":>l};
heldOptionAppendTo[x_]:=Function[{v},AppendTo[v,x],HoldFirst];
ffff[x_,OptionsPattern[]]:=OptionValue[Automatic,Automatic,"a",heldOptionAppendTo[x]]  

Some other similar useful functions. The great thing about Leonid's method and the OptionValue fourth argument is that we truly have access to the optional variable without an evaluation leak.

heldOptionSetKey[key_,value_]:=Function[{v},v[key]=value,HoldFirst];
heldOptionSetPart[part__,value_]:=Function[{v},v[[part]]=value,HoldFirst];
heldOptionIncrement[]:=Function[{v},v++,HoldFirst];
$\endgroup$

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.