# method -- make a new method function

## Synopsis

• Usage:
f = method()
• Optional inputs:
• TypicalValue => a type, default value Thing, the type of the value returned by f, typically. This information is used only to build documentation automatically, and is stored in the hash table typicalValues.
• Options => a list, default value null, a list of options J => v, where J is the name of an optional argument for f, and v is its default value. The list of options could be also replaced by the corresponding OptionTable. Specifying true here indicates that option handling is done by the individual methods, while still allowing dispatching to methods based on types of arguments to be done. The individual methods may have various sets of acceptable option names, possibly empty. See making new functions with optional arguments.
• Binary => , default value false, whether the method is to be binary: for three arguments or more the result will be computed by calling binary methods installed for f with two arguments at a time.
• Dispatch => ..., default value {Thing, Thing, Thing, Thing}, the method for getting a list of types from the parameters; the value of this option should be Thing or Type to indicate that a sequence should be regarded as a single argument, or, if the elements of a sequence are to be regarded as separate parameters, a list whose elements are Thing or Type. Parameters corresponding to Thing or to a position beyond the end of the list are dispatched according to their class, whereas parameters corresponding to Type are expected to be types (actually, hash tables) and are used directly in the search for methods; see inheritance.
• Outputs:
• f, a new method function, , , , or

## Description

The code above creates a method function that takes up to four arguments, looking up the appropriate method according to the classes of the arguments, with inheritance. To install a method for two arguments, (x,y), of classes X and Y, use code like this:
     f(X,Y) := (x,y) -> ...
where '...' represents the body of the function you wish to install. The syntax for one or three arguments is analogous. See := for details.
 i1 : f = method() o1 = f o1 : MethodFunction i2 : f ZZ := x -> -x; i3 : f(ZZ,String) := (n,s) -> concatenate(n:s); i4 : f(String,ZZ,String) := (s,n,t) -> concatenate(s," : ",toString n," : ",t); i5 : f 44 o5 = -44 i6 : f(5,"abcd ") o6 = abcd abcd abcd abcd abcd  i7 : f("foo",88,"bar") o7 = foo : 88 : bar

In the following example we install a asymmetric method to illustrate the left-associative order of evaluation for a binary method function.

 i8 : p = method(Binary => true, TypicalValue => List) o8 = p o8 : MethodFunctionBinary i9 : p(ZZ,ZZ) := p(List,ZZ) := (i,j) -> {i,j} o9 = -*Function[stdio:9:33-9:39]*- o9 : FunctionClosure i10 : p(1,2) o10 = {1, 2} o10 : List i11 : p(1,2,3,4,5,6) o11 = {{{{{1, 2}, 3}, 4}, 5}, 6} o11 : List
By default, at most four arguments (in a sequence) can be handled by a method function, and the types have to be considered separately when installing methods. In this example, we define a method function that treats a sequence as a single argument, and we install a method for handling such arguments.
 i12 : g = method(Dispatch => Thing); i13 : g ZZ := i -> -i; i14 : g Sequence := S -> reverse S; i15 : g 44 o15 = -44 i16 : g(3,4,5,6) o16 = (6, 5, 4, 3) o16 : Sequence
Here we define a method whose first argument is to be a type. It will convert its second argument to that type.
 i17 : h = method(Dispatch => {Type}) o17 = h o17 : MethodFunction i18 : h(QQ,ZZ) := (QQ,n) -> n/1; i19 : h(RR,ZZ) := (RR,n) -> n + 0.; i20 : h(ZZ,ZZ) := (ZZ,n) -> n; i21 : h(ZZ,14) o21 = 14 i22 : h(QQ,14) o22 = 14 o22 : QQ i23 : h(RR,14) o23 = 14 o23 : RR (of precision 53)

In the next example we make a linear function of a single real variable whose coefficients are provided as optional arguments named Slope and Intercept, with default value 1.

 i24 : r = method(Options => {Slope => 1, Intercept => 1}) o24 = r o24 : MethodFunctionWithOptions

The methods installed for this method function should be written in the form opts -> args -> (...). The argument opts will be assigned a hash table of type OptionTable containing the optional argument names and their current values. For example, in the body of the function, the current value for the argument named b can be recovered with opts#b, or with opts.b, in case b is known to be a global symbol. Be careful not to change the value of b, or the code will stop working; it would be a good idea to protect it.

 i25 : r RR := o -> x -> o.Slope * x + o.Intercept o25 = -*Function[stdio:25:11-25:35]*- o25 : FunctionClosure i26 : r(5.) o26 = 6 o26 : RR (of precision 53) i27 : r(5.,Slope=>100) o27 = 501 o27 : RR (of precision 53)

The default option table for r can be recovered with the function options. The options given to method can be recovered with methodOptions.

 i28 : options r o28 = OptionTable{Intercept => 1} Slope => 1 o28 : OptionTable i29 : methodOptions r o29 = OptionTable{Binary => false } Dispatch => {Thing, Thing, Thing, Thing} Options => {Slope => 1, Intercept => 1} TypicalValue => Thing o29 : OptionTable

In the next example we define a method function that leaves option processing to the individual methods.

 i30 : s = method(Options => true) o30 = s o30 : MethodFunctionWithOptions i31 : s ZZ := { Slope => 17 } >> o -> x -> o.Slope * x o31 = -*Function[/usr/share/Macaulay2/Core/option.m2:14:20-16:34]*- o31 : FunctionClosure i32 : s RR := { Intercept => 11 } >> o -> x -> x + o.Intercept o32 = -*Function[/usr/share/Macaulay2/Core/option.m2:14:20-16:34]*- o32 : FunctionClosure i33 : s 100 o33 = 1700 i34 : s 1000. o34 = 1011 o34 : RR (of precision 53) i35 : options s i36 : options(s,ZZ) o36 = OptionTable{Slope => 17} o36 : OptionTable i37 : options(s,RR) o37 = OptionTable{Intercept => 11} o37 : OptionTable

For now, one installs a method function for s with no non-optional arguments using installMethod:

 i38 : installMethod(s,{ Slope => 1234 } >> o -> () -> o.Slope) o38 = -*Function[/usr/share/Macaulay2/Core/option.m2:14:20-16:34]*- o38 : FunctionClosure i39 : s() o39 = 1234 i40 : s(Slope => 4) o40 = 4

## For the programmer

The object method is .