Trick that I sometimes find useful is "inheriting" of default option value from another symbol using delayed rule like:
optName :> OptionValue[anotherSymbol, optName]
With f defined as:
ClearAll[f]; Options[f] = {optA -> 1, optB -> 1, optC -> 1}; f[x_, opts : OptionsPattern[]] := OptionValue[{optA, optB, optC}]
We can define g in following way:
ClearAll[g]; (* Inherit all options from f *) Options[g] = # :> OptionValue[f, #] & @@@ Options[f]; (* Change default values of some of them. *) SetOptions[g, optA -> 0, optB -> 0]; g[x_, opts : OptionsPattern[]] := f[x, opts, Options[g]]
Basically it works as previous solutions
g[x] (* {0, 0, 1} *) g[x, optA -> 2, optC -> 2] (* {2, 0, 2} *)
g inherits options from f in all situations, not only in above specific function call.
OptionValue[g, {optA, optB, optC}] (* {0, 0, 1} *)
If you change default options of f, then non-overridden default options of g will inherit this change in all circumstances:
SetOptions[f, optC -> 2]; g[x] (* {0, 0, 2} *) OptionValue[g, {optA, optB, optC}] (* {0, 0, 2} *)
Also at any time you can decide to change default value of any option (not only those overridden when g was defined) only on g without affecting f.
SetOptions[g, optC -> 0]; g[x] (* {0, 0, 0} *) f[x] (* {1, 1, 2} *)
You can also, at any time, decide to use inherited option value:
SetOptions[g, optA :> OptionValue[f, optA]]; g[x] (* {1, 0, 0} *)
Options[g] = Options[f]; SetOptions[g, {optA -> 0, optB -> 0}](instead of filtering). The most annoying thing for me about this solution is that if I laterSetOptionsonf, the change won't be inherited byg. But this is what happens with builtins too (e.g.PlotvsGraphics) and the workaround is rather verbose and complicated. $\endgroup$OptA -> OptionValue[OptA], optB -> OptionValue[optB]in the call tofis indeed necessary? $\endgroup$