Parameter passing provides a way of explicitly controlling some or all of the variable context transferred between M routines.
M uses parameter passing for:
A DO command with parameters
Extrinsic functions and special variables
Parameter passing is optional on DO commands.
Parameter passing uses two argument lists: the actuallist that specifies the parameters that M passes to an invoked routine, and the formalist that specifies the local variables to receive or associate with the parameters.
An actuallist specifies the parameters M passes to the invoked routine. The actuallist contains a list of zero or more parameters enclosed in parentheses, immediately following a DO or extrinsic function.
Is made up of items separated by commas
Contains expressions and/or actualnames. Items may be missing, that is, two commas may appear next to each other, with nothing between them.
Must be used in an invocation of a label with a formallist, except in the case of extrinsic special variables.
Must not contain undefined variables.
Must not have more items than a formallist with which it is used.
May contain the same item in more than one position.
This example illustrates a DO with parameters. The actuallist contains:
3 - a numeric literal
X - a local variable
.RESULT - an actualname
An actualname starts with a leading period (.) delimiter, followed by an unsubscripted local variable name. Actualnames identify variables that are passed by reference, as described in a subsequent section. While expressions in an actualname are evaluated when control is transferred to a formallabel, the variables identified by actualnames are not; therefore, they do not need to be defined at the time control is transferred.
A formallist specifies the variables M uses to hold passed values. A formallist contains a list of zero or more parameters enclosed in parentheses, immediately following a label.
Is made up of items separated by commas.
Contains unsubscripted local variable names.
Must be used and only used with a label invoked with an actuallist or an extrinsic.
May contain undefined variables.
May have more items than an actuallist with which it is used.
Must not contain the same item in more than one position.
Must contain at least as many items as the actuallist with which it is used.
MULT(MP,MC,RES) SET RES=MP*MC QUIT RES
In this example, illustrating a simple parameterized routine, the formallist contains the following items:
An example in the section describing "Actuallists" shows an invocation that matches this routine.
M performs an implicit NEW on the formallist names and replaces the formallist items with the actuallist items.
M provides the actuallist values to the invoked procedure by giving each element in the formallist the value or reference provided by the corresponding element in the actuallist. M associates the first name in the formallist with the first item in the actuallist, the second name in the formallist with the second item in the actuallist and so on. If the actuallist is shorter than the formallist, M ensures that the formallist items with no corresponding value are in effect NEWed. If the formallist item has no corresponding item in the actuallist (indicated by two adjacent commas in the actuallist), that item in the formallist becomes undefined.
If the actuallist item is an expression and the corresponding formallist variable is an array, parameter passing does not affect the subscripted elements of the array. If an actualname corresponds to a formallist variable, M reflects array operations on the formallist variable, by reference, in the variable specified by the actualname.
M treats variables that are not part of the formallist as if parameter passing did not exist (i.e., M makes them available to the invoked routine).
M initiates execution at the first command following the formallabel.
A QUIT command terminates execution of the invoked routine. At the time of the QUIT, M restores the formallist items to the values they had at the invocation of the routine.
In the case where a variable name appears as an actualname in the actuallist, and also as a variable in the formallist, the restored value reflects any change made by reference.
A QUIT from a DO does not take an argument, while a QUIT from an extrinsic must have an argument. This represents one of the two major differences between the DO command with parameters and the extrinsics. M returns the value of the QUIT command argument as the value of the extrinsic function or special variable. The other difference is that M stacks $TEST for extrinsics.
SET X=30,Z="Hello" DO WRTSQR(X) ZWRITE QUIT WRTSQR(Z) SET Z=Z*Z WRITE Z,! QUIT
900 X=30 Z="Hello"
M passes the actuallist values to the invoked routine using two parameter-passing mechanisms:
Call-by-Value - where expressions appear
Call-by-Reference - where actualnames appear
A call-by-value passes a copy of the value of the actuallist expression to the invoked routine by assigning the copy to a formallist variable. If the parameter is a variable, the invoked routine may change that variable. However, because M constructs that variable to hold the copy, it deletes the variable holding the copy when the QUIT restores the prior formallist values. This also means that changes to the variable by the invoked routine do not affect the value of the variable in the invoking routine.
SET X=30 DO SQR(X) ZWRITE QUIT SQR(Z)SET Z=Z*Z QUIT
A period followed by a name identifies an actualname and causes a call-by-reference.
A call-by-reference passes a pointer to the variable of the invoked routine so operations on the assigned formallist variable also act on the actualname variable. Changes, including KILLs to the formallist variable, immediately have the same affect on the corresponding actualname variable. This means that M passes changes to formallist variables in the invoked routine back to the invoking routine as changes in actualname variables.
SET X=30 DO SQR(.X) ZWRITE QUIT SQR(Z)SET Z=Z*Z QUIT
The standard does not provide for indirection of a labelref because the syntax has an ambiguity.
This example could be:
An invocation of the label specified by X with a parameter of 1.
An invocation of the label specified by X(1) with no parameter list.
GT.M processes the latter interpretation as illustrated in the following example.
SET A(1)="CUBE",X=5 DO @A(1)(.X) WRITE X,! QUIT CUBE(C);cube a variable SET C=C*C*C QUIT
Produces the result:
GT.M follows analogous syntax for routine indirection:
DO ^@X(A) invokes the routine specified by X(A).
DO ^@(X)(A) invokes the routine specified by X and passes the parameter A.
DO ^@X(A)(A) invokes the routine specified by X(A) and passes the parameter A.