RE: Re: a technique for options

*To*: mathgroup at smc.vnet.net*Subject*: [mg71711] RE: [mg71635] Re: a technique for options*From*: "Ingolf Dahl" <ingolf.dahl at telia.com>*Date*: Mon, 27 Nov 2006 04:04:33 -0500 (EST)

Hi Daniel and Chris, Do you agree that this is a tree? In[1]:= tree = {{{{}, {{}, {}}}, {{}, {}}, {{}, {{}, {}}}}}; It's made out of Options as you can see: In[2]:= OptionQ[tree] Out[2]:= True Now you can try ReplaceAll apply In[3]:= apple /. {tree} Out[3]:= {{{{apple, {apple, apple}}, {apple, apple}, {apple, {apple, apple}}}}} Then you have apples for your apple pie! If this you shook, just take a look in section 2.5.1 in the book! Now seriously, I have tried to check the command Plot, which should be a typical command with options. It does not seem to matter if you supply options as rules, as lists of rules or as nested lists of rules. So probably internally in the command the options are extracted essentially in this way, with PlotRange as example: pr = PlotRange /. Flatten[{opts}] /. Options[Plot] If the list of options is not flattened, ReplaceAll might replace PlotRange with a list of replaced or un-replaced values, as in the apple example above. But if this method with Flatten is followed also in user-written functions, it should be OK to specify the options arguments by opts___?OptionQ . Please correct me if I am wrong here, because in that case I have to rewrite a lot of functions. I agree with Chris that the section 2.3.10 should be corrected (Include the OptionQ test, and Flatten[{opts}]!) Best regards Ingolf Dahl And by the way, its fun to play, and a laugh and an apple keeps the doctor away! > -----Original Message----- > From: dh [mailto:dh at metrohm.ch] > Sent: den 25 november 2006 11:37 > To: mathgroup at smc.vnet.net > Subject: [mg71635] Re: a technique for options > > Hi Chris, > there seems to be an misunderstanding. The technique in the > book works well, if you feed it the requested input. If the > input is wrong, it obvioulsy does not work. > Consider ____, this means zero or more arguments. If it is > used as explained in the book, it means zero or more Rules > and not "list of rules". > Unfortunately OptionQ gives True if you feed it a rule or a > list of rules, leading to the error message you saw. > Therefore, to check if you really have rules, you could e.g. > use opts___?(Head[#]==Rule&) Daniel > > Chris Chiasson wrote: > > I noticed this a few months ago, but I am just getting around to > > programming this way, and I'd like to share it with you: > > > > OptionQ evaluates to True for an option or a list of > options. A lot of > > built in functions can handle their options given as lists: > > > > Plot[x,{x,0,1},{PlotStyle->Blue}] > > > > However, users (myself included), seem to be writing code > that ignores > > this aspect of option handling. I blame this ( like all my other > > Mathematica failings :-] ) squarely on the documentation, > specifically > > section 2.3.10. > > > > BTW, I just noticed that OptionQ, like StringQ, does not > have a help > > browser entry. > > > > Here is an example from that section on writing functions > that take options: > > > > ----------------------------------------------------------------- > > f[x_, opts___] := value > > a typical definition for a function with zero or more named > optional > > arguments name/.{opts}/.Options[f] replacements used to get > the value > > of a named optional argument in the body of the function > > ----------------------------------------------------------------- > > > > There are two things "wrong" with the example. The first, and > > non-serious, problem is that the named pattern opts isn't > checked with > > OptionQ. The second, and more serious, problem is that the > result of > > name/.{opts}/.Options[f] will likely be different if the > user feeds an > > option list to the function instead of the expected option sequence. > > > > People may feel that it is a waste of time to support such > a calling > > convention, but it is actually rather easy to do robustly, AFAIK. > > > > The technique involves the exploitation of Flatten (and the > fact that > > rules aren't lists)... Here is an example: > > > > Options[f]={Precision->40}; > > f[x_,callOpts___?OptionQ]:= > > With[{opts=Flatten[{callOpts,Options[f]}]},N[x,Precision/.opts]] > > > > f[5] > > f[5,Precision->10] > > f[5,{Precision->20}] > > > > 5.000000000000000000000000000000000000000 > > > > 5.000000000 > > > > 5.0000000000000000000 > > > > Here is what would happen on the last call if the user chose the > > technique in the Mathematica Book: > > > > System`Dump`$MessagesInHelpBrowserAreKnown=False; > > N[5,Precision/.{{Precision->20}}/.Options@f] > > > > N::arg: Argument {20} is not of the form {precision, accuracy}. > > > > N[5,{20}] > > > >