function

Definition of a function.
Methods of Java objects as functions.
Calling a function.
Fixing the number of inputs.
The return statement.
Functions are first class objects.
Function definition in m-files.
Subfunctions and Nested functions.
static variables.

Definition of a function

The basic syntax for the definition of a function in Mathnium is as follows:
     function [out1,out2,..]=functionname(in1,in2,..)
	statements
     end 
or
     function (out1,out2,..)=functionname(in1,in2, ..)
	statements
     end 

Here in1, in2, etc. are the input arguments and out1,out2, etc. are the output arguments. There is no explicit limit on the number of input arguments or output arguments. The statements obviously use the values of the inputs to compute the outputs.

If a function does not need any inputs or outputs, the corresponding clauses of the the leading line of the function may be omitted. Thus, for example

function myfunction(x,y)
  disp(x,y)
end
just displays the inputs, and the function
function [y,z]=readinput
   y=input('what is y')
   z=input('what is z')
end

prompts the user to input the values of the outputs.

It is also possible to define the so-called inline functions. The definition
a=@(in1,in2,...)(expression)

is equivalent, in the more elaborate form above, to

function (y)=a(in1,in2,...)
	y=expression
end
The inline form is convenient for defining simple functions, especially for calling functions that require a function as an argument.
>>x=fzero(@(x)sin(x)*x-1,rand(1,1))
>>x
    1.1142
>>sin(x)*x
    1.0000

Importing methods of Java objects as functions

Methods of Java classes in the class path can be easily imported as functions.

Calling a function

Once a function is defined, it can be called by using the syntax
     [argout1,argout2,..]=functionname(argin1,argin2, ..)
or
     (argout1,argout2,..)=functionname(argin1,argin2, ..)

The inputs to a function are passed by value. What this means is that if you have defined a function which modifies an input in any way, when the function is called the modification is not made to the variable used as the input argument. The following trivial example illustrates this:

>>function [y]=myfunction(x)
>   x=x+10
>   y=x
>end
>>u=20;
>>[v]=myfunction(u)
>>v
   30
>>u
   20
Thus, even though the function modifies the value of the input, the value of the input argument in the call,i.e., u, is retained even after the call.

The outputs to a function are passed by reference. For example:

>>function [y]=defaulty(x)
>   if(y==null);y=x;end
>end
>>u=20;
>>[u]=defaulty(10)
>>u
   20
>>u=null;
>>[u]=defaulty(10)
>>u
   10
Thus, the initial value of an output argument during the execution of a function is its value in the context of the caller immediately prior to the call, and any modifications in the value during the execution of the function are are retained when the function terminates.

Fixing the number of input arguments

All the inputs and outputs to a function as defined above are optional. Thus the number of inputs in the call to a function may be less than the number of inputs in the function definition. If such is the case, all the remaining inputs are undefined on entry to the function.

The number of input arguments used in the call to a function are available as the value of the variable nargin and, likewise, nargout is set to the number of outputs.

>>function [u,v]=func(x,y,z)
>nargin,nargout,NL
>end
>>[u]=func()
         0  1
>>[u, v]= func(2,3)
         2  2
>>[u] = func(2,3,4)
         3  1
>>[u] = func(2,3,4,5)
Error The function func needs at most 3 input arguments but given 4
Thus typically it is necessary to check if the caller has specified the necessary number of input arguments. To avoid having to do this explicitly, the input arguments can be divided into two parts: the required input arguments and the optional inputs, and the two can be separated by a vertical bar in the function definition.
 
>>function func1(x, y | u)
>  nargin,NL
>end
>>func1(2,3)
         2
>>func1(2,3,4)
         3
>>func1(2)
Error The function func1 needs at least 2 input arguments but only 1 is specified

The return statement.

The return statement may be used to terminate the execution of the statements in a function, and return the thread of execution to the caller's context. The return expression statement also has the same effect, except that it additionally sets the value of the first output of the function to expression.

>>function [y]=defaulty(x)
>   if(y==null);y=x;end
>end
>>// Same as defaulty  above, but uses return expression.
>>function [y]=defaulty1(x)
>   if(y==null);return x;end
>end
>>// Same as defaulty  above, but uses both return expression
>>// and return
>>function [y]=defaulty2(x)
>   if(y!=null);return;end
>   return x;	
>end

Functions are like any other data type.

Like numbers or strings or any other data type, functions may be used as arguments in call to functions, returned as outputs of functions, and used as elements of cell arrays or fields of objects or structs, except that the name must be preceded by the symbol @ or $ to suppress the interpretation of the name as a function call with no inputs.
>>// This function returns a function.
>>function func(fname)
>if(fname=="sin")
>    return $sin
>else if(fname=="cos")
>    return @cos
>else if(fname=="tan")
>    return $tan
>else
>   error("Invalid function name")
>end
>end
>>func("sin")(pi/3)
           0.866
>>func("cos")(pi/3)
             0.5
>>func("tan")(pi/3)
          1.7321
>>// This function assumes the first input to be a function.
>>function myfeval(func,x)
>    return func(x)
>end
>>myfeval($sin,pi/3)
           0.866
>>myfeval($cos,pi/3)
             0.5
>>myfeval($tan,pi/3)
          1.7321
>>myfeval(@tan,pi/4)
               1

Creating function objects.

Many functions in the Mathnium library require function objects as an argument. There are a number of ways to create such objects.

Function definition in m-files

If a function myfunction is defined in a file called myfunction.m (as is the recommended practice) and the directory of this file is added to the search path of the interpreter by calling addpath, the function is automatically included in the current global context, and the call to the function, even if it is not defined at the time, will result in the execution of the file myfunction.m to load the function.

Subfunctions and nested functions

An m-file may contain more than one function definition. However, only the first function in the file is available in the global context. All the other functions are subfunctions, available only in the context of the functions defined in the file.

A function may be defined within another function. A nested function is available only within the context of the function in which it is defined. Note that arbitrary levels of nesting are not allowed: a nested function may not be defined within another nested function.

>>showfile("func1.m")
function func1(x)        # This function is visible golobally.
   return func2(x)
end
function func2(x)  # This is a subfunction, visible only to func1 and func2.
   return @func3
   function func3() # This is a  nested function, visible only to func2.
	return x+10;
   end
end
>>a=func1(10)
>>a(2)
   12
>>// Note that func2 (a subfunction) and func3 (a nested function) are undefined
>>// in the global context.
>>func2
  null
>>func3
  null

static/persistent and global variables in functions

Normally, any variables defined within a function are not visible outside the function. However, this behavior can be overridden by declaring a variable to be global.

>>function func(x)
>  global u
>  u=x+10
>end
>>function func1()
>  global u
>  return u+2
>end
>>func(10)
>>func1()
   22
>>u
   20

It is not a good programming practice to use too many global variables, and so they should be used sparingly and with care.

A variable can be declared to be static or, equivalently, persistent, to retain its value during successive calls.

>>function currentDate()
>import java.text.*
>// The dateformatter object is created only the first time
>// the function is called, and it retains its value for successive
>// calls.
>   static dateformatter=new SimpleDateFormat("yyyy-MM-dd  HH:mm:ss")
>   return dateformatter.format(Calendar.getInstance().getTime())
>end
>>currentDate()
2008-03-29  20:36:38
>>currentDate()
2008-03-29  20:36:40