Message Boards Message Boards

0
|
1578 Views
|
4 Replies
|
0 Total Likes
View groups...
Share
Share this post:

How to find all options used for a function?

Posted 1 year ago

If I have a custom function with optional values, how can I find all the options used for a particular call?

If I write:

ClearAll[f];
Options[f]={opt1->42,opt2->""};
f[x_,options:OptionsPattern[]]:=Module[{},
   Row[{"x = ",x,", options: ",options}]
];
f[4711,opt2->"this is opt2"]
(* ==> x = 4711, options: opt2->this is opt2 *)

... I only get the options that were actually used by the caller.

To get all options, I have only found the following solution:

ClearAll[f];
Options[f]={opt1->42,opt2->""};
f[x_,options:OptionsPattern[]]:=Module[{allOptions},
   allOptions=First[#]->OptionValue[First[#]]&/@Options[f];
   Row[{"x = ",x,", All options: ",allOptions,", Caller options: ",options}]
];
f[4711,opt2->"this is opt2"]
(* ==> x = 4711, All options: {opt1->42,opt2->this is opt2}, Caller options: opt2->this is opt2 *)

This works, but it is not very elegant. Is there a better way?

POSTED BY: Werner Geiger
4 Replies
Posted 1 year ago

You could do something like this:

Options[f] = {opt1 -> "opt1 default value", 
   opt2 -> "opt2 default value"};
f[x_, options : OptionsPattern[]] :=
 Grid[
  {{"x =", x},
   {"default options:", Options[f]},
   {"passed options:", {options}},
   {"current options:", Merge[Join[Options[f], {options}], Last]}},
  Alignment -> {{Right, Left}}]

But I feel like there is something else going on. If you want to inspect/manipulate a list of things passed by the caller, then that list should probably be a "normal" argument rather than options. It's kind of the whole point of options that you get some argument values "for free" (using OptionValue) without having to inspect the actual argument list.

POSTED BY: Eric Rimbey
Posted 1 year ago

Yes Eric, you are right. Actually I use this only during testing of complicated functions where I use to start with Echo all parameters.

Your solution with Merge is even more lengthy than mine.

POSTED BY: Werner Geiger
Posted 1 year ago

I guess it ultimately doesn't matter, but I'm confused by your assertion that my solution was longer than yours.

First[#] -> OptionValue[First[#]] & /@ Options[f]

is longer than

Merge[Join[Options[f], {options}], Last]

and when you add in all of the other stuff you used, like assignment and Module, the difference is significant. If you're referring to my putting together a Grid structure, that was just to demonstrate the different views on the options. Presumably you'd only use the bit that you wanted. And there is more to elegance than number of characters used. Merge is a natural operation to use with rules and associations. What you did was take a list of rules, destructure it, and restructure it, which is much more complicated semantically. I suspect that there is even a more elegant way than what I did--I don't deal with optional arguments very often.

POSTED BY: Eric Rimbey
Posted 1 year ago

Ok, Eric, you are right. But this question of elegance is not really important for my point. I thought I missed some build in function or option similar zu Options[f] which directly gives all the options used in a function, either explicitly set by the caller or taken from the defaults.

Thanks for your interest and help.

POSTED BY: Werner Geiger
Reply to this discussion
Community posts can be styled and formatted using the Markdown syntax.
Reply Preview
Attachments
Remove
or Discard

Group Abstract Group Abstract